Skip to content

Commit 07bde70

Browse files
committed
Initial changes for a large packetbuffer allocation
1 parent fbe1835 commit 07bde70

File tree

2 files changed

+34
-11
lines changed

2 files changed

+34
-11
lines changed

src/system/SystemPacketBuffer.cpp

+26-8
Original file line numberDiff line numberDiff line change
@@ -470,7 +470,7 @@ void PacketBuffer::AddRef()
470470
#endif // !CHIP_SYSTEM_CONFIG_USE_LWIP
471471
}
472472

473-
PacketBufferHandle PacketBufferHandle::New(size_t aAvailableSize, uint16_t aReservedSize)
473+
PacketBufferHandle PacketBufferHandle::New(size_t aAvailableSize, uint16_t aReservedSize, bool aIsLarge)
474474
{
475475
// Adding three 16-bit-int sized numbers together will never overflow
476476
// assuming int is at least 32 bits.
@@ -488,7 +488,14 @@ PacketBufferHandle PacketBufferHandle::New(size_t aAvailableSize, uint16_t aRese
488488

489489
CHIP_SYSTEM_FAULT_INJECT(FaultInjection::kFault_PacketBufferNew, return PacketBufferHandle());
490490

491-
if (aAvailableSize > UINT16_MAX || lAllocSize > PacketBuffer::kMaxSizeWithoutReserve || lBlockSize > UINT16_MAX)
491+
#if INET_CONFIG_ENABLE_TCP_ENDPOINT
492+
if (aIsLarge && lAllocSize > CHIP_CONFIG_LARGE_PAYLOAD_MAX_SIZE)
493+
{
494+
ChipLogError(chipSystemLayer, "PacketBuffer: allocation too large.");
495+
return PacketBufferHandle();
496+
}
497+
#endif // INET_CONFIG_ENABLE_TCP_ENDPOINT
498+
if (!aIsLarge && (aAvailableSize > UINT16_MAX || lAllocSize > PacketBuffer::kMaxSizeWithoutReserve || lBlockSize > UINT16_MAX))
492499
{
493500
ChipLogError(chipSystemLayer, "PacketBuffer: allocation too large.");
494501
return PacketBufferHandle();
@@ -548,16 +555,17 @@ PacketBufferHandle PacketBufferHandle::New(size_t aAvailableSize, uint16_t aRese
548555
}
549556

550557
PacketBufferHandle PacketBufferHandle::NewWithData(const void * aData, size_t aDataSize, uint16_t aAdditionalSize,
551-
uint16_t aReservedSize)
558+
uint16_t aReservedSize, bool aIsLarge)
552559
{
553-
if (aDataSize > UINT16_MAX)
560+
bool isOutOfSizeBounds = (aIsLarge ? aDataSize > UINT32_MAX : aDataSize > UINT16_MAX);
561+
if (isOutOfSizeBounds)
554562
{
555563
ChipLogError(chipSystemLayer, "PacketBuffer: allocation too large.");
556564
return PacketBufferHandle();
557565
}
558566
// Since `aDataSize` fits in uint16_t, the sum `aDataSize + aAdditionalSize` will not overflow.
559567
// `New()` will only return a non-null buffer if the total allocation size does not overflow.
560-
PacketBufferHandle buffer = New(aDataSize + aAdditionalSize, aReservedSize);
568+
PacketBufferHandle buffer = New(aDataSize + aAdditionalSize, aReservedSize, aIsLarge);
561569
if (buffer.mBuffer != nullptr)
562570
{
563571
memcpy(buffer.mBuffer->payload, aData, aDataSize);
@@ -671,7 +679,7 @@ PacketBufferHandle PacketBufferHandle::PopHead()
671679
return PacketBufferHandle(head);
672680
}
673681

674-
PacketBufferHandle PacketBufferHandle::CloneData() const
682+
PacketBufferHandle PacketBufferHandle::CloneData(bool aIsLarge) const
675683
{
676684
PacketBufferHandle cloneHead;
677685

@@ -680,7 +688,17 @@ PacketBufferHandle PacketBufferHandle::CloneData() const
680688
uint16_t originalDataSize = original->MaxDataLength();
681689
uint16_t originalReservedSize = original->ReservedSize();
682690

683-
if (originalDataSize + originalReservedSize > PacketBuffer::kMaxSizeWithoutReserve)
691+
#if INET_CONFIG_ENABLE_TCP_ENDPOINT
692+
// If buffer is intended to be large, check against max size for large
693+
// allocations.
694+
if (aIsLarge && originalDataSize + originalReservedSize > CHIP_CONFIG_LARGE_PAYLOAD_MAX_SIZE)
695+
{
696+
return PacketBufferHandle();
697+
}
698+
#endif // INET_CONFIG_ENABLE_TCP_ENDPOINT
699+
// If buffer is not intended to be large, check against max size for
700+
// packets meant to go over MRP.
701+
if (!aIsLarge && originalDataSize + originalReservedSize > PacketBuffer::kMaxSizeWithoutReserve)
684702
{
685703
// The original memory allocation may have provided a larger block than requested (e.g. when using a shared pool),
686704
// and in particular may have provided a larger block than we are able to request from PackBufferHandle::New().
@@ -694,7 +712,7 @@ PacketBufferHandle PacketBufferHandle::CloneData() const
694712
originalDataSize = static_cast<uint16_t>(PacketBuffer::kMaxSizeWithoutReserve - originalReservedSize);
695713
}
696714

697-
PacketBufferHandle clone = PacketBufferHandle::New(originalDataSize, originalReservedSize);
715+
PacketBufferHandle clone = PacketBufferHandle::New(originalDataSize, originalReservedSize, aIsLarge);
698716
if (clone.IsNull())
699717
{
700718
return PacketBufferHandle();

src/system/SystemPacketBuffer.h

+8-3
Original file line numberDiff line numberDiff line change
@@ -613,32 +613,37 @@ class DLL_EXPORT PacketBufferHandle
613613
*
614614
* On success, it is guaranteed that \c AvailableDataSize() is no less than \a aAvailableSize.
615615
*
616+
* @param[in] aIsLarge Explicitly indicates if the buffer allocation is meant to be large(exceeding kMaxSize)
616617
* @param[in] aAvailableSize Minimum number of octets to for application data (at `Start()`).
617618
* @param[in] aReservedSize Number of octets to reserve for protocol headers (before `Start()`).
618619
*
619620
* @return On success, a PacketBufferHandle to the allocated buffer. On fail, \c nullptr.
620621
*/
621-
static PacketBufferHandle New(size_t aAvailableSize, uint16_t aReservedSize = PacketBuffer::kDefaultHeaderReserve);
622+
static PacketBufferHandle New(size_t aAvailableSize, uint16_t aReservedSize = PacketBuffer::kDefaultHeaderReserve, bool aIsLarge = false);
622623

623624
/**
624625
* Allocates a packet buffer with initial contents.
625626
*
626627
* @param[in] aData Initial buffer contents.
628+
* @param[in] aIsLarge Explicitly indicates if the buffer allocation is meant to be large(exceeding kMaxSize)
627629
* @param[in] aDataSize Size of initial buffer contents.
628630
* @param[in] aAdditionalSize Size of additional application data space after the initial contents.
629631
* @param[in] aReservedSize Number of octets to reserve for protocol headers.
630632
*
631633
* @return On success, a PacketBufferHandle to the allocated buffer. On fail, \c nullptr.
632634
*/
633635
static PacketBufferHandle NewWithData(const void * aData, size_t aDataSize, uint16_t aAdditionalSize = 0,
634-
uint16_t aReservedSize = PacketBuffer::kDefaultHeaderReserve);
636+
uint16_t aReservedSize = PacketBuffer::kDefaultHeaderReserve, bool aIsLarge = false);
635637

636638
/**
637639
* Creates a copy of a packet buffer (or chain).
638640
*
641+
* @param[in] aIsLarge Explicitly indicates if the buffer cloning is intended
642+
* on a large buffer exceeding
643+
* kMaxSize.
639644
* @returns empty handle on allocation failure. Otherwise, the returned buffer has the same sizes and contents as the original.
640645
*/
641-
PacketBufferHandle CloneData() const;
646+
PacketBufferHandle CloneData(bool aIsLarge = false) const;
642647

643648
/**
644649
* Perform an implementation-defined check on the validity of a PacketBufferHandle.

0 commit comments

Comments
 (0)