/* Ċ Ġ* ĠCopyright Ġ@ Ġ 2 0 1 9 Ġ 8 x 8 , ĠInc Ċ Ġ* Ċ Ġ* ĠLicensed Ġunder Ġthe ĠApache ĠLicense , ĠVersion Ġ 2 . 0 Ġ( the Ġ" License "); Ċ Ġ* Ġyou Ġmay Ġnot Ġuse Ġthis Ġfile Ġexcept Ġin Ġcompliance Ġwith Ġthe ĠLicense . Ċ Ġ* ĠYou Ġmay Ġobtain Ġa Ġcopy Ġof Ġthe ĠLicense Ġat Ċ Ġ* Ċ Ġ* ĠĠĠĠ Ġhttp :// www . apache . org / licenses / LICENSE - 2 . 0 Ċ Ġ* Ċ Ġ* ĠUnless Ġrequired Ġby Ġapplicable Ġlaw Ġor Ġagreed Ġto Ġin Ġwriting , Ġsoftware Ċ Ġ* Ġdistributed Ġunder Ġthe ĠLicense Ġis Ġdistributed Ġon Ġan Ġ" AS ĠIS " ĠBASIS , Ċ Ġ* ĠWITHOUT ĠWARRANTIES ĠOR ĠCONDITIONS ĠOF ĠANY ĠKIND , Ġeither Ġexpress Ġor Ġimplied . Ċ Ġ* ĠSee Ġthe ĠLicense Ġfor Ġthe Ġspecific Ġlanguage Ġgoverning Ġpermissions Ġand Ċ Ġ* Ġlimitations Ġunder Ġthe ĠLicense . Ċ Ġ*/ Ċ package Ġorg . j its i . video bridge . cc . vp 9 Ċ Ċ import Ġorg . j its i . nl j . codec . v px . V px Utils . Companion . apply Extended Picture Id Delta Ċ import Ġorg . j its i . nl j . rtp . Video R tp Packet Ċ import Ġorg . j its i . nl j . rtp . codec . vp 9 . Vp 9 Packet Ċ import Ġorg . j its i . nl j . util . set And Extend Ċ import Ġkotlin . collections . ArrayList Ċ Ċ /** Ċ Ġ* ĠGroups Ġtogether Ġsome ĠR TP / VP 9 Ġfields Ġthat Ġrefer Ġto Ġa Ġspecific Ġincoming ĠV P 9 Ċ Ġ* Ġpicture , Ġwhich Ġmay Ġconsist Ġof Ġmultiple Ġframes Ġ( of Ġdifferent Ġspatial Ġlayers ). Ċ Ġ* Ċ Ġ* ĠInstances Ġof Ġthis Ġclass Ġare Ġ* NOT * Ġthread Ġsafe . Ċ Ġ* Ċ Ġ* Ġ@ author ĠJon athan ĠL enn ox Ċ Ġ*/ Ċ class ĠV p 9 Picture ( packet : ĠV p 9 Packet , Ġindex : ĠInt ) Ġ{ ĊĠĠĠ Ġval Ġframes Ġ= ĠArrayList < Vp 9 Frame ?> () ĊĊĠĠĠ Ġinit Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġsid Ġ= Ġpacket . effective Spatial Layer Index ĊĊĠĠĠĠĠĠĠ Ġset Frame At Sid ( Vp 9 Frame ( packet , Ġindex ), Ġsid ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġfun Ġframe ( sid : ĠInt ) Ġ= Ġframes . get OrNull ( sid ) ĊĊĠĠĠ Ġfun Ġframe ( packet : ĠV p 9 Packet ) Ġ= Ġframe ( packet . effective Spatial Layer Index ) ĊĊĠĠĠ Ġprivate Ġfun Ġset Frame At Sid ( frame : ĠV p 9 Frame , Ġsid : ĠInt ) Ġ= ĊĠĠĠĠĠĠĠ Ġframes . set And Extend ( sid , Ġframe , Ġnull ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠReturn Ġthe Ġfirst Ġ( lowest - sid , Ġear liest Ġin Ġdecoding Ġorder ) Ġframe Ġthat Ġwe 've Ġreceived Ġso Ġfar . ĊĠĠĠĠ Ġ* ĠA Ġvalid Ġpicture Ġmust Ġhave Ġat Ġleast Ġone Ġframe , Ġso Ġthis Ġwill Ġalways Ġreturn Ġone . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġprivate Ġfun Ġfirst Frame (): ĠV p 9 Frame Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġf Ġ= Ġframes . find Ġ{ Ġf Ġ-> Ġf Ġ!= Ġnull Ġ} ĊĠĠĠĠĠĠĠ Ġcheck ( f Ġ!= Ġnull ) Ġ{ Ġ" Picture Ġmust Ġhave Ġat Ġleast Ġone Ġframe " Ġ} ĊĠĠĠĠĠĠĠ Ġreturn Ġf ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠReturn Ġthe Ġlast Ġ( highest - sid , Ġear liest Ġin Ġdecoding Ġorder ) Ġframe Ġthat Ġwe 've Ġreceived Ġso Ġfar . ĊĠĠĠĠ Ġ* ĠA Ġvalid Ġpicture Ġmust Ġhave Ġat Ġleast Ġone Ġframe , Ġso Ġthis Ġwill Ġalways Ġreturn Ġone . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġprivate Ġfun Ġlast Frame (): ĠV p 9 Frame Ġ{ ĊĠĠĠĠĠĠĠ Ġval Ġf Ġ= Ġframes . find Last Ġ{ Ġf Ġ-> Ġf Ġ!= Ġnull Ġ} ĊĠĠĠĠĠĠĠ Ġcheck ( f Ġ!= Ġnull ) Ġ{ Ġ" Picture Ġmust Ġhave Ġat Ġleast Ġone Ġframe " Ġ} ĊĠĠĠĠĠĠĠ Ġreturn Ġf ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġval Ġs src : ĠLong ĊĠĠĠĠĠĠĠ Ġget () Ġ= Ġfirst Frame (). ss rc ĊĊĠĠĠ Ġval Ġtimestamp : ĠLong ĊĠĠĠĠĠĠĠ Ġget () Ġ= Ġfirst Frame (). timestamp ĊĊĠĠĠ Ġval Ġtemporal Layer : ĠInt ĊĠĠĠĠĠĠĠ Ġget () Ġ= Ġfirst Frame (). temporal Layer ĊĊĠĠĠ Ġval Ġear liest Known SequenceNumber : ĠInt ĊĠĠĠĠĠĠĠ Ġget () Ġ= Ġfirst Frame (). ear liest Known SequenceNumber ĊĊĠĠĠ Ġval Ġlatest Known SequenceNumber : ĠInt ĊĠĠĠĠĠĠĠ Ġget () Ġ= Ġlast Frame (). latest Known SequenceNumber ĊĊĠĠĠ Ġval Ġpicture Id : ĠInt ĊĠĠĠĠĠĠĠ Ġget () Ġ= Ġfirst Frame (). picture Id ĊĊĠĠĠ Ġval Ġindex : ĠInt ĊĠĠĠĠĠĠĠ Ġget () Ġ= Ġfirst Frame (). index ĊĊĠĠĠ Ġval Ġtl 0 PIC IDX : ĠInt ĊĠĠĠĠĠĠĠ Ġget () Ġ= Ġfirst Frame (). tl 0 PIC IDX ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠRemember Ġanother Ġpacket Ġof Ġthis Ġframe . ĊĠĠĠĠ Ġ* ĠNote : Ġthis Ġassumes Ġevery Ġpacket Ġis Ġreceived Ġonly Ġonce , Ġi . e . Ġa Ġfilter ĊĠĠĠĠ Ġ* Ġlike Ġ[ org . j its i . nl j . transform . node . incoming . Padding Termination ] Ġis Ġin Ġuse . ĊĠĠĠĠ Ġ* Ġ@ param Ġpacket ĠThe Ġpacket Ġto Ġremember . Ġ ĠThis Ġshould Ġbe Ġa Ġpacket Ġwhich ĊĠĠĠĠ Ġ* Ġhas Ġtested Ġtrue Ġwith Ġ[ matches Picture ]. ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġadd Packet ( packet : ĠV p 9 Packet ): ĠPacket Insertion Result Ġ{ ĊĠĠĠĠĠĠĠ Ġrequire ( matches Picture ( packet )) Ġ{ Ġ" Non - matching Ġpacket Ġadded Ġto Ġpicture " Ġ} ĊĊĠĠĠĠĠĠĠ Ġval Ġsid Ġ= Ġpacket . effective Spatial Layer Index ĊĊĠĠĠĠĠĠĠ Ġval Ġf Ġ= Ġframe ( packet ) ĊĊĠĠĠĠĠĠĠ Ġif Ġ( f Ġ!= Ġnull ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġf . add Packet ( packet ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġreturn ĠPacket Insertion Result ( f , Ġthis , Ġfalse ) ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġval Ġnew F Ġ= ĠV p 9 Frame ( packet , Ġindex ) ĊĊĠĠĠĠĠĠĠ Ġset Frame At Sid ( new F , Ġsid ) ĊĊĠĠĠĠĠĠĠ Ġreturn ĠPacket Insertion Result ( new F , Ġthis , Ġtrue ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠDetermines Ġwhether Ġthe Ġ[ Video R tp Packet ] Ġthat Ġis Ġspecified Ġas Ġan ĊĠĠĠĠ Ġ* Ġargument Ġis Ġpart Ġof Ġthe ĠV P 9 Ġpicture Ġthat Ġis Ġrepresented Ġby Ġthis ĊĠĠĠĠ Ġ* Ġ[ Vp 9 Picture ] Ġinstance . ĊĠĠĠĠ Ġ* ĊĠĠĠĠ Ġ* Ġ@ param Ġpkt Ġthe Ġ[ Video R tp Packet ] Ġinstance Ġto Ġcheck Ġwhether Ġit 's Ġpart ĊĠĠĠĠ Ġ* Ġof Ġthe ĠV P 9 Ġpicture Ġthat Ġis Ġrepresented Ġby Ġthis Ġ[ Vp 9 Picture ] ĊĠĠĠĠ Ġ* Ġinstance . ĊĠĠĠĠ Ġ* Ġ@ return Ġtrue Ġif Ġthe Ġ[ Video R tp Packet ] Ġthat Ġis Ġspecified Ġas Ġan ĊĠĠĠĠ Ġ* Ġargument Ġis Ġpart Ġof Ġthe ĠV P 9 Ġpicture Ġthat Ġis Ġrepresented Ġby Ġthis ĊĠĠĠĠ Ġ* Ġ[ Vp 9 Picture ] Ġinstance , Ġfalse Ġotherwise . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġprivate Ġfun Ġmatches SS RC ( pkt : ĠVideo R tp Packet ): ĠBoolean Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn Ġs src Ġ== Ġpkt . ss rc ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠChecks Ġwhether Ġthe Ġspecified ĠR TP Ġpacket Ġis Ġpart Ġof Ġthis Ġframe . ĊĠĠĠĠ Ġ* ĊĠĠĠĠ Ġ* Ġ@ param Ġpkt Ġthe ĠR TP Ġpacket Ġto Ġcheck Ġwhether Ġit 's Ġpart Ġof Ġthis Ġframe . ĊĠĠĠĠ Ġ* Ġ@ return Ġtrue Ġif Ġthe Ġspecified ĠR TP Ġpacket Ġis Ġpart Ġof Ġthis Ġframe , Ġfalse ĊĠĠĠĠ Ġ* Ġotherwise . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġmatches Picture ( pkt : ĠV p 9 Packet ): ĠBoolean Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn Ġmatches SS RC ( pkt ) Ġ&& Ġtimestamp Ġ== Ġpkt . timestamp ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠValid ates Ġthat Ġthe Ġspecified ĠR TP Ġpacket Ġconsistently Ġmatches Ġall Ġthe ĊĠĠĠĠ Ġ* Ġparameters Ġof Ġthis Ġpicture Ġ( or Ġthe Ġappropriate Ġframe ). ĊĠĠĠĠ Ġ* ĊĠĠĠĠ Ġ* ĠThis Ġcan Ġbe Ġuseful Ġfor Ġdi agn osing Ġinvalid Ġstreams Ġif Ġthis Ġfails Ġwhen ĊĠĠĠĠ Ġ* Ġ[ matches Picture ] Ġis Ġtrue . ĊĠĠĠĠ Ġ* ĊĠĠĠĠ Ġ* Ġ@ param Ġpkt Ġthe ĠR TP Ġpacket Ġto Ġcheck Ġwhether Ġits Ġparameters Ġmatch Ġthis Ġframe . ĊĠĠĠĠ Ġ* Ġ@ throws ĠRuntimeException Ġif Ġthe Ġspecified ĠR TP Ġpacket Ġis Ġinconsistent Ġwith Ġthis Ġframe ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġvalidate Consistency ( pkt : ĠV p 9 Packet ) Ġ{ ĊĊĠĠĠĠĠĠĠ Ġval Ġf Ġ= Ġframe ( pkt ) ĊĠĠĠĠĠĠĠ Ġif Ġ( f Ġ!= Ġnull ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġf . validate Consistency ( pkt ) ĊĠĠĠĠĠĠĠĠĠĠĠ Ġreturn ĊĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġif Ġ( temporal Layer Ġ== Ġpkt . temporal Layer Index Ġ&& Ġtl 0 PIC IDX Ġ== Ġpkt . TL 0 PIC IDX Ġ&& Ġpicture Id Ġ== Ġpkt . picture Id ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ/* ĠTODO : Ġalso Ġcheck Ġstart , Ġend , Ġseq Ġnums ? Ġ*/ ĊĠĠĠĠĠĠĠĠĠĠĠ Ġreturn ĊĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġthrow ĠRuntimeException ( ĊĠĠĠĠĠĠĠĠĠĠĠ Ġbuild String Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġwith ( pkt ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġappend (" Packet Ġs src Ġ$ ss rc , Ġseq Ġ$ sequence Number , Ġpicture Ġid Ġ$ picture Id , Ġtimestamp Ġ$ timestamp Ġ") ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġappend (" is Ġnot Ġconsistent Ġwith Ġpicture Ġ$ ss rc , Ġ") ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġappend (" seq Ġ$ ear liest Known SequenceNumber -$ latest Known SequenceNumber Ġ") ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġappend (" picture Ġid Ġ$ picture Id , Ġtimestamp Ġ$ timestamp : Ġ") ĊĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġvar Ġcompl ained Ġ= Ġfalse ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( temporal Layer Ġ!= Ġpkt . temporal Layer Index ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġappend (" packet Ġtemporal Ġlayer Ġ${ pkt . temporal Layer Index } Ġ!= Ġframe Ġtemporal Ġlayer Ġ$ temporal Layer ") ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcompl ained Ġ= Ġtrue ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( tl 0 PIC IDX Ġ!= Ġpkt . TL 0 PIC IDX ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( compl ained ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġappend ("; Ġ") ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġappend (" packet ĠTL 0 PIC IDX Ġ${ pkt . TL 0 PIC IDX } Ġ!= Ġframe ĠTL 0 PIC IDX Ġ$ tl 0 PIC IDX ") ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġcompl ained Ġ= Ġtrue ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( picture Id Ġ!= Ġpkt . picture Id ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġif Ġ( compl ained ) Ġ{ ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġappend ("; Ġ") ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġappend (" packet ĠPicture ID Ġ${ pkt . picture Id } Ġ!= Ġframe ĠPicture ID Ġ$ picture Id ") ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĠĠĠĠĠĠĠ Ġ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠCheck Ġwhether Ġthis Ġpicture Ġis Ġimmediately Ġafter Ġanother Ġone , Ġaccording ĊĠĠĠĠ Ġ* Ġto Ġtheir Ġextended Ġpicture ĠIDs . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġis Immediate ly After ( other Picture : ĠV p 9 Picture ): ĠBoolean Ġ{ ĊĠĠĠĠĠĠĠ Ġreturn Ġpicture Id Ġ== ĊĠĠĠĠĠĠĠĠĠĠĠ Ġapply Extended Picture Id Delta ( other Picture . picture Id , Ġ 1 ) ĊĠĠĠ Ġ} Ċ } Ċ Ċ /** Ċ Ġ* ĠThe Ġresult Ġof Ġcalling Ġ[ insert Packet ] Ċ Ġ*/ Ċ class ĠPacket Insertion Result ( ĊĠĠĠ Ġ/** ĠThe Ġframe Ġcorresponding Ġto Ġthe Ġpacket Ġthat Ġwas Ġinserted . Ġ*/ ĊĠĠĠ Ġval Ġframe : ĠV p 9 Frame , ĊĠĠĠ Ġ/** ĠThe Ġpicture Ġcorresponding Ġto Ġthe Ġpacket Ġthat Ġwas Ġinserted . Ġ Ġ*/ ĊĠĠĠ Ġval Ġpicture : ĠV p 9 Picture , ĊĠĠĠ Ġ/** ĠWhether Ġinserting Ġthe Ġpacket Ġcreated Ġa Ġnew Ġframe . Ġ Ġ*/ ĊĠĠĠ Ġval Ġis New Frame : ĠBoolean , ĊĠĠĠ Ġ/** ĠWhether Ġinserting Ġthe Ġpacket Ġcaused Ġa Ġreset Ġ Ġ*/ ĊĠĠĠ Ġval Ġis Reset : ĠBoolean Ġ= Ġfalse Ċ ) Ċ