0

I need to extract some information from a Transport Stream like PID, PAT, PMT, etc.

I found an example code to get the PID:

pid = ((buf[1] << 8) | (buf[2] & 0xff)) & 0x1fff;

But I could not understand the reason to get the buf[1] and shift 8 to the left side because to get the PID information I need get the 5 last bits from the buf[1] and all 8 from the buf[2]. I tested the code and the result was good. I just want to understand the mean of this first part: buf[1] << 8 in the equation. Could someone help me?

Ryan K
  • 3,985
  • 4
  • 39
  • 42
Leandro P
  • 213
  • 4
  • 12

2 Answers2

0

Lets say your PID is 4660 or 0x1234. so buf[1] = 0x12, and buf[2] = 0x34

Lest do the math int a = 0x12 | 0x32 what is a set to? a = 0x36.

0x36 != 0x1234. What we need is int a = 0x1200 | 0x34 to get 0x1234

How do we turn 0x12 into 0x1200? We shift it left by 8 bits. (buf[1] << 8)

szatmary
  • 29,969
  • 8
  • 44
  • 57
0

The PID is 13 bits long.

The buffer buf is a byte array. Each element is 8 bits.

The smallest Java integer type to hold a PID is the short (16-bit signed integer). buf[1] << 8 promotes the byte to an int (4 bytes) while shifting so you now have enough space to hold the result.

  buf[1] = XXXXXXXX
  buf[2] = YYYYYYYY

  buf[1] << 8 
  shifted 8 positions to the left in a 32-bit int

  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
   +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
   |0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 X X X X X X X X 0 0 0 0 0 0 0 0| 
   +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+


  (buf[1] << 8) | buf[2]

  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
   +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
   |0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 X X X X X X X X Y Y Y Y Y Y Y Y| 
   +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+


  ((buf[1] << 8) | buf[2]) & 0x1fff

  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
   +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
   |0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 X X X X X Y Y Y Y Y Y Y Y| 
   +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+

buf[2] & 0xff is needed because in Java all bytes are signed and you need the unsigned int value of the byte. Finally the whole thing is masked with 0x1fff to keep the relevant 13 bits. If you want a short you must cast the resulting int.

aergistal
  • 29,947
  • 5
  • 70
  • 92
  • Thank you @aergistal! Now I got the ideia. – Leandro P Sep 19 '15 at 23:47
  • Do you know any website that I can get more information about bitmasks? Like, I have more information to extract each one with different size of bits but I don't have the masks for each one – Leandro P Sep 19 '15 at 23:57
  • You can see examples for all bitwise operations on Wikipedia: https://en.wikipedia.org/wiki/Bitwise_operation. `|` is `OR`, `&` is AND and so on. – aergistal Sep 20 '15 at 00:02