⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 mpeg1or2videostreamframer.cpp

📁 流媒体传输协议的实现代码,非常有用.可以支持rtsp mms等流媒体传输协议
💻 CPP
📖 第 1 页 / 共 2 页
字号:
};unsigned MPEG1or2VideoStreamParser::parseVideoSequenceHeader(Boolean haveSeenStartCode) {#ifdef DEBUG  fprintf(stderr, "parsing video sequence header\n");#endif  unsigned first4Bytes;  if (!haveSeenStartCode) {    while ((first4Bytes = test4Bytes()) != VIDEO_SEQUENCE_HEADER_START_CODE) {#ifdef DEBUG      fprintf(stderr, "ignoring non video sequence header: 0x%08x\n", first4Bytes);#endif      get1Byte(); setParseState(PARSING_VIDEO_SEQUENCE_HEADER);          // ensures we progress over bad data    }    first4Bytes = get4Bytes();  } else {    // We've already seen the start code    first4Bytes = VIDEO_SEQUENCE_HEADER_START_CODE;  }  save4Bytes(first4Bytes);  // Next, extract the size and rate parameters from the next 8 bytes  unsigned paramWord1 = get4Bytes();  save4Bytes(paramWord1);  unsigned next4Bytes = get4Bytes();#ifdef DEBUG  unsigned short horizontal_size_value   = (paramWord1&0xFFF00000)>>(32-12);  unsigned short vertical_size_value     = (paramWord1&0x000FFF00)>>8;  unsigned char aspect_ratio_information = (paramWord1&0x000000F0)>>4;#endif  unsigned char frame_rate_code          = (paramWord1&0x0000000F);  usingSource()->fFrameRate = frameRateFromCode[frame_rate_code];#ifdef DEBUG  unsigned bit_rate_value                = (next4Bytes&0xFFFFC000)>>(32-18);  unsigned vbv_buffer_size_value         = (next4Bytes&0x00001FF8)>>3;  fprintf(stderr, "horizontal_size_value: %d, vertical_size_value: %d, aspect_ratio_information: %d, frame_rate_code: %d (=>%f fps), bit_rate_value: %d (=>%d bps), vbv_buffer_size_value: %d\n", horizontal_size_value, vertical_size_value, aspect_ratio_information, frame_rate_code, usingSource()->fFrameRate, bit_rate_value, bit_rate_value*400, vbv_buffer_size_value);#endif  // Now, copy all bytes that we see, up until we reach a GROUP_START_CODE  // or a PICTURE_START_CODE:  do {    saveToNextCode(next4Bytes);  } while (next4Bytes != GROUP_START_CODE && next4Bytes != PICTURE_START_CODE);    setParseState((next4Bytes == GROUP_START_CODE)		? PARSING_GOP_HEADER_SEEN_CODE : PARSING_PICTURE_HEADER);  // Compute this frame's timestamp by noting how many pictures we've seen  // since the last GOP header:  usingSource()->computePresentationTime(fPicturesSinceLastGOP);  // Save this video_sequence_header, in case we need to insert a copy  // into the stream later:  saveCurrentVSH();  return curFrameSize();}unsigned MPEG1or2VideoStreamParser::parseGOPHeader(Boolean haveSeenStartCode) {  // First check whether we should insert a previously-saved  // 'video_sequence_header' here:  if (needToUseSavedVSH()) return useSavedVSH();#ifdef DEBUG  fprintf(stderr, "parsing GOP header\n");#endif  unsigned first4Bytes;  if (!haveSeenStartCode) {    while ((first4Bytes = test4Bytes()) != GROUP_START_CODE) {#ifdef DEBUG      fprintf(stderr, "ignoring non GOP start code: 0x%08x\n", first4Bytes);#endif      get1Byte(); setParseState(PARSING_GOP_HEADER);          // ensures we progress over bad data    }    first4Bytes = get4Bytes();  } else {    // We've already seen the GROUP_START_CODE    first4Bytes = GROUP_START_CODE;  }  save4Bytes(first4Bytes);  // Next, extract the (25-bit) time code from the next 4 bytes:  unsigned next4Bytes = get4Bytes();  unsigned time_code = (next4Bytes&0xFFFFFF80)>>(32-25);#if defined(DEBUG) || defined(DEBUG_TIMESTAMPS)  Boolean drop_frame_flag     = (time_code&0x01000000) != 0;#endif  unsigned time_code_hours    = (time_code&0x00F80000)>>19;  unsigned time_code_minutes  = (time_code&0x0007E000)>>13;  unsigned time_code_seconds  = (time_code&0x00000FC0)>>6;  unsigned time_code_pictures = (time_code&0x0000003F);#if defined(DEBUG) || defined(DEBUG_TIMESTAMPS)  fprintf(stderr, "time_code: 0x%07x, drop_frame %d, hours %d, minutes %d, seconds %d, pictures %d\n", time_code, drop_frame_flag, time_code_hours, time_code_minutes, time_code_seconds, time_code_pictures);#endif#ifdef DEBUG  Boolean closed_gop  = (next4Bytes&0x00000040) != 0;  Boolean broken_link = (next4Bytes&0x00000020) != 0;  fprintf(stderr, "closed_gop: %d, broken_link: %d\n", closed_gop, broken_link);#endif  // Now, copy all bytes that we see, up until we reach a PICTURE_START_CODE:  do {    saveToNextCode(next4Bytes);  } while (next4Bytes != PICTURE_START_CODE);  // Record the time code:  usingSource()->setTimeCode(time_code_hours, time_code_minutes,			     time_code_seconds, time_code_pictures,			     fPicturesSinceLastGOP);  fPicturesSinceLastGOP = 0;  // Compute this frame's timestamp:  usingSource()->computePresentationTime(0);    setParseState(PARSING_PICTURE_HEADER);  return curFrameSize();}inline Boolean isSliceStartCode(unsigned fourBytes) {  if ((fourBytes&0xFFFFFF00) != 0x00000100) return False;  unsigned char lastByte = fourBytes&0xFF;  return lastByte <= 0xAF && lastByte >= 1;}unsigned MPEG1or2VideoStreamParser::parsePictureHeader() {#ifdef DEBUG  fprintf(stderr, "parsing picture header\n");#endif  // Note that we've already read the PICTURE_START_CODE  // Next, extract the temporal reference from the next 4 bytes:  unsigned next4Bytes = get4Bytes();  unsigned short temporal_reference = (next4Bytes&0xFFC00000)>>(32-10);  unsigned char picture_coding_type = (next4Bytes&0x00380000)>>19;#ifdef DEBUG  unsigned short vbv_delay          = (next4Bytes&0x0007FFF8)>>3;  fprintf(stderr, "temporal_reference: %d, picture_coding_type: %d, vbv_delay: %d\n", temporal_reference, picture_coding_type, vbv_delay);#endif  fSkippingCurrentPicture = fIFramesOnly && picture_coding_type != 1;  if (fSkippingCurrentPicture) {    // Skip all bytes that we see, up until we reach a slice_start_code:    do {      skipToNextCode(next4Bytes);    } while (!isSliceStartCode(next4Bytes));  } else {    // Save the PICTURE_START_CODE that we've already read:    save4Bytes(PICTURE_START_CODE);    // Copy all bytes that we see, up until we reach a slice_start_code:    do {      saveToNextCode(next4Bytes);    } while (!isSliceStartCode(next4Bytes));  }    setParseState(PARSING_SLICE);  fCurrentSliceNumber = next4Bytes&0xFF;  // Record the temporal reference:  fCurPicTemporalReference = temporal_reference;  // Compute this frame's timestamp:  usingSource()->computePresentationTime(fCurPicTemporalReference);  if (fSkippingCurrentPicture) {    return parse(); // try again, until we get a non-skipped frame  } else {     return curFrameSize();  }}unsigned MPEG1or2VideoStreamParser::parseSlice() {  // Note that we've already read the slice_start_code:  unsigned next4Bytes = PICTURE_START_CODE|fCurrentSliceNumber;#ifdef DEBUG_SLICE  fprintf(stderr, "parsing slice: 0x%08x\n", next4Bytes);#endif  if (fSkippingCurrentPicture) {    // Skip all bytes that we see, up until we reach a code of some sort:    skipToNextCode(next4Bytes);  } else {    // Copy all bytes that we see, up until we reach a code of some sort:    saveToNextCode(next4Bytes);  }    // The next thing to parse depends on the code that we just saw:  if (isSliceStartCode(next4Bytes)) { // common case    setParseState(PARSING_SLICE);    fCurrentSliceNumber = next4Bytes&0xFF;  } else {    // Because we don't see any more slices, we are assumed to have ended    // the current picture:    ++fPicturesSinceLastGOP;    ++usingSource()->fPictureCount;    usingSource()->fPictureEndMarker = True; // HACK #####    switch (next4Bytes) {    case SEQUENCE_END_CODE: {      setParseState(PARSING_VIDEO_SEQUENCE_HEADER);      break;    }    case VIDEO_SEQUENCE_HEADER_START_CODE: {      setParseState(PARSING_VIDEO_SEQUENCE_HEADER_SEEN_CODE);      break;    }    case GROUP_START_CODE: {      setParseState(PARSING_GOP_HEADER_SEEN_CODE);      break;    }    case PICTURE_START_CODE: {      setParseState(PARSING_PICTURE_HEADER);      break;    }    default: {      usingSource()->envir() << "MPEG1or2VideoStreamParser::parseSlice(): Saw unexpected code "			    << (void*)next4Bytes << "\n";      setParseState(PARSING_SLICE); // the safest way to recover...      break;    }    }  }  // Compute this frame's timestamp:  usingSource()->computePresentationTime(fCurPicTemporalReference);  if (fSkippingCurrentPicture) {    return parse(); // try again, until we get a non-skipped frame  } else {     return curFrameSize();  }}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -