Repository: pion/rtp
Pull request #30 (2020-01-05 16:25:11)

Add transport-cc extension
Add transport-cc extension

#### Description

#### Reference issue
https://tools.ietf.org/html/draft-holmer-rmcat-transport-wide-cc-extensions-01#page-3


codecov-io: # [Codecov](https://codecov.io/gh/pion/rtp/pull/30?src=pr&el=h1) Report
> Merging [#30](https://codecov.io/gh/pion/rtp/pull/30?src=pr&el=desc) into [master](https://codecov.io/gh/pion/rtp/commit/99e26d872d7e3c8b7c91830b4f78d2f372f38c2f?src=pr&el=desc) will **increase** coverage by `0.1%`.
> The diff coverage is `83.33%`.

[![Impacted file tree graph](https://codecov.io/gh/pion/rtp/pull/30/graphs/tree.svg?width=650&token=4KrbiBsspj&height=150&src=pr)](https://codecov.io/gh/pion/rtp/pull/30?src=pr&el=tree)

```diff
@@            Coverage Diff            @@
##           master      #30     +/-   ##
=========================================
+ Coverage   80.35%   80.45%   +0.1%     
=========================================
  Files           9       10      +1     
  Lines         336      348     +12     
=========================================
+ Hits          270      280     +10     
- Misses         57       58      +1     
- Partials        9       10      +1
```


| [Impacted Files](https://codecov.io/gh/pion/rtp/pull/30?src=pr&el=tree) | Coverage Δ | |
|---|---|---|
| [transportccextension.go](https://codecov.io/gh/pion/rtp/pull/30/diff?src=pr&el=tree#diff-dHJhbnNwb3J0Y2NleHRlbnNpb24uZ28=) | `83.33% <83.33%> (ø)` | |

------

[Continue to review full report at Codecov](https://codecov.io/gh/pion/rtp/pull/30?src=pr&el=continue).
> **Legend** - [Click here to learn more](https://docs.codecov.io/docs/codecov-delta)
> `Δ = absolute <relative> (impact)`, `ø = not affected`, `? = missing data`
> Powered by [Codecov](https://codecov.io/gh/pion/rtp/pull/30?src=pr&el=footer). Last update [99e26d8...da2d09d](https://codecov.io/gh/pion/rtp/pull/30?src=pr&el=lastupdated). Read the [comment docs](https://docs.codecov.io/docs/pull-request-comments).

maxhawkins: Left you some feedback!

I haven't contributed to the project in a while so I don't want to approve until Sean or someone takes a look, but overall it looks good.
adwpc: > What's this for? LGTM otherwise

packetizer_test.go import
Sean-Der: @adwpc LGTM! Thanks for grabbing, would you mind adding the tests max mentioned and squashing into one commit. Then happy to approve :) sorry I am slow on this.
adwpc: > @adwpc LGTM! Thanks for grabbing, would you mind adding the tests max mentioned and squashing into one commit. Then happy to approve :) sorry I am slow on this. I had to read the RFC myself, never implemented any of the congestion-control algos myself.

Added test and one commit

Patch:
diff --git a/README.md b/README.md
index d839b2f..87d75cb 100644
--- a/README.md
+++ b/README.md
@@ -39,6 +39,7 @@ Check out the **[contributing wiki](https://github.com/pion/webrtc/wiki/Contribu
 * [Hugo Arregui](https://github.com/hugoArregui)
 * [Raphael Derosso Pereira](https://github.com/raphaelpereira)
 * [Atsushi Watanabe](https://github.com/at-wat)
+* [adwpc](https://github.com/adwpc) *add transport-cc extension*
 
 ### License
 MIT License - see [LICENSE](LICENSE) for full text
diff --git a/go.mod b/go.mod
index 1046d76..90c4b73 100644
--- a/go.mod
+++ b/go.mod
@@ -1,3 +1,5 @@
 module github.com/pion/rtp
 
 go 1.12
+
+require github.com/stretchr/testify v1.4.0
diff --git a/go.sum b/go.sum
index e69de29..e863f51 100644
--- a/go.sum
+++ b/go.sum
@@ -0,0 +1,10 @@
+github.com/davecgh/go-spew v1.1.0 h1:ZDRjVQ15GmhC3fiQ8ni8+OwkZQO4DARzQgrnXU1Liz8=
+github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
+github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
+github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
+github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
+github.com/stretchr/testify v1.4.0 h1:2E4SXV/wtOkTonXsotYi4li6zVWxYlZuYNCXe9XRJyk=
+github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4=
+gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
+gopkg.in/yaml.v2 v2.2.2 h1:ZCJp+EgiOT7lHqUV2J862kp8Qj64Jo6az82+3Td9dZw=
+gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI=
diff --git a/transportccextension.go b/transportccextension.go
new file mode 100644
index 0000000..fd585c5
--- /dev/null
+++ b/transportccextension.go
@@ -0,0 +1,46 @@
+package rtp
+
+import (
+	"encoding/binary"
+	"errors"
+)
+
+const (
+	transportCCExtensionSize = 4
+)
+
+var (
+	errTooSmall = errors.New("buffer too small")
+)
+
+// TransportCCExtension is a extension payload format in
+// https://tools.ietf.org/html/draft-holmer-rmcat-transport-wide-cc-extensions-01
+// 0                   1                   2                   3
+// 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+// |       0xBE    |    0xDE       |           length=1            |
+// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+// |  ID   | L=1   |transport-wide sequence number | zero padding  |
+// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
+type TransportCCExtension struct {
+	ID                uint8
+	TransportSequence uint16
+}
+
+// Marshal serializes the members to buffer
+func (t *TransportCCExtension) Marshal() ([]byte, error) {
+	buf := make([]byte, transportCCExtensionSize)
+	buf[0] = t.ID<<4&0xf0 + 1
+	binary.BigEndian.PutUint16(buf[1:3], t.TransportSequence)
+	return buf, nil
+}
+
+// Unmarshal parses the passed byte slice and stores the result in the members
+func (t *TransportCCExtension) Unmarshal(rawData []byte) error {
+	if len(rawData) < transportCCExtensionSize {
+		return errTooSmall
+	}
+	t.ID = rawData[0] >> 4
+	t.TransportSequence = binary.BigEndian.Uint16(rawData[1:3])
+	return nil
+}


Test patch:
diff --git a/transportccextension_test.go b/transportccextension_test.go
new file mode 100644
index 0000000..2164430
--- /dev/null
+++ b/transportccextension_test.go
@@ -0,0 +1,63 @@
+package rtp
+
+import (
+	"bytes"
+	"testing"
+)
+
+func TestTransportCCExtensionTooSmall(t *testing.T) {
+	t1 := TransportCCExtension{}
+
+	rawData := []byte{}
+
+	if err := t1.Unmarshal(rawData); err != errTooSmall {
+		t.Fatal("err != errTooSmall")
+	}
+}
+
+func TestTransportCCExtension(t *testing.T) {
+	t1 := TransportCCExtension{}
+
+	rawData := []byte{
+		0x31, 0x00, 0x02, 0x00,
+	}
+
+	if err := t1.Unmarshal(rawData); err != nil {
+		t.Fatal("Unmarshal error on extension data")
+	}
+
+	t2 := TransportCCExtension{
+		ID:                3,
+		TransportSequence: 2,
+	}
+
+	if t1 != t2 {
+		t.Error("Unmarshal failed")
+	}
+
+	dstData, _ := t2.Marshal()
+	if !bytes.Equal(dstData, rawData) {
+		t.Error("Marshal failed")
+	}
+}
+
+func TestTransportCCExtensionExtraBytes(t *testing.T) {
+	t1 := TransportCCExtension{}
+
+	rawData := []byte{
+		0x31, 0x00, 0x02, 0x00, 0xff, 0xff,
+	}
+
+	if err := t1.Unmarshal(rawData); err != nil {
+		t.Fatal("Unmarshal error on extension data")
+	}
+
+	t2 := TransportCCExtension{
+		ID:                3,
+		TransportSequence: 2,
+	}
+
+	if t1 != t2 {
+		t.Error("Unmarshal failed")
+	}
+}