📄 programstream.c
字号:
perror(infilename); exit(1); } strcpy(cur_filename, infilename); rv = fstat(infilefd, &statbuf); if (rv == -1) { perror("fstat"); exit(1); } disk_buf = (uint8_t *)mmap(NULL, statbuf.st_size, PROT_READ, MAP_SHARED, infilefd, 0); close(infilefd); if(disk_buf == MAP_FAILED) { perror("mmap"); exit(1); } infilelen = statbuf.st_size;#ifdef HAVE_MADVISE rv = madvise(disk_buf, infilelen, MADV_SEQUENTIAL); if(rv == -1) { perror("madvise"); exit(1); }#endif DPRINTF(1, "All mmap systems ok!\n"); new_file++;}char *stream_opts[] = {#define OPT_STREAM_NR 0 "nr",#define OPT_FILE 1 "file",#define OPT_SUBID 2 "subid", NULL};int attach_ctrl_shm(int shmid){ char *shmaddr; if(shmid >= 0) { if((shmaddr = shmat(shmid, NULL, SHM_SHARE_MMU)) == (void *)-1) { perror("demux: attach_ctrl_data(), shmat()"); return -1; } ctrl_data_shmid = shmid; ctrl_data = (ctrl_data_t*)shmaddr; ctrl_time = (ctrl_time_t *)(shmaddr+sizeof(ctrl_data_t)); } return 0;}int main(int argc, char **argv){ int c, rv; struct sigaction sig; char *options; char *opt_value; int stream_nr; int subid; char *file; uint8_t stream_id; int lost_sync = 1; program_name = argv[0]; GET_DLEVEL(); init_id_reg(STREAM_DISCARD); /* Parse command line options */ while ((c = getopt(argc, argv, "v:a:s:i:d:m:o:p:h?")) != EOF) { switch (c) { case 'v': stream_nr = -1; file = NULL; options = optarg; while (*options != '\0') { switch(getsubopt(&options, stream_opts, &opt_value)) { case OPT_STREAM_NR: if(opt_value == NULL) { exit(1); } stream_nr = atoi(opt_value); break; case OPT_FILE: if(opt_value == NULL) { exit(1); } file = opt_value; break; default: fprintf(stderr, "*demux: Unknown suboption\n"); exit(1); break; } } if((stream_nr == -1)) { fprintf(stderr, "*demux: Missing suboptions\n"); exit(1); } if((stream_nr < 0) && (stream_nr > 0xf)) { fprintf(stderr, "*demux: Invalid stream nr\n"); exit(1); } stream_id = (0xe0 | stream_nr); if(file != NULL) { video_file = fopen(file,"w"); if(!video_file) { perror(optarg); exit(1); } id_add(stream_id, 0, STREAM_DECODE, -1, NULL, video_file); } else { fprintf(stderr, "Video stream %d disabled\n", stream_nr); id_add(stream_id, 0, STREAM_DISCARD, -1, NULL, NULL); } break; case 'p': stream_nr = -1; file = NULL; subid = -1; options = optarg; while (*options != '\0') { switch(getsubopt(&options, stream_opts, &opt_value)) { case OPT_SUBID: if(opt_value == NULL) { exit(1); } subid = strtol(opt_value, NULL, 0); break; case OPT_STREAM_NR: if(opt_value == NULL) { exit(1); } stream_nr = atoi(opt_value); break; case OPT_FILE: if(opt_value == NULL) { exit(1); } file = opt_value; break; default: fprintf(stderr, "*demux: Unknown suboption\n"); exit(1); break; } } if((subid == -1)) { fprintf(stderr, "*demux: Missing suboptions\n"); exit(1); } else if(subid < 0 || subid > 0xff) { fprintf(stderr, "*demux: subid out of range\n"); exit(1); } if((stream_nr == -1)) { fprintf(stderr, "*demux: Missing suboptions\n"); exit(1); } if(!(stream_nr < subid) || (subid | stream_nr) > 0xff) { fprintf(stderr, "*demux: subid/stream_nr combination invalid\n"); exit(1); } stream_id = (subid | stream_nr); if(file != NULL) { ps1_file = fopen(file,"w"); if(!ps1_file) { perror(optarg); exit(1); } id_add(MPEG2_PRIVATE_STREAM_1, stream_id, STREAM_DECODE, -1, NULL, ps1_file); } else { fprintf(stderr, "Private stream 1 subid %d disabled\n", stream_nr); id_add(MPEG2_PRIVATE_STREAM_1, stream_id, STREAM_DISCARD, -1, NULL, NULL); } break; case 'a': stream_nr = -1; file = NULL; options = optarg; while (*options != '\0') { switch(getsubopt(&options, stream_opts, &opt_value)) { case OPT_STREAM_NR: if(opt_value == NULL) { exit(1); } stream_nr = atoi(opt_value); break; case OPT_FILE: if(opt_value == NULL) { exit(1); } file = opt_value; break; default: fprintf(stderr, "*demux: Unknown suboption\n"); exit(1); break; } } if((stream_nr == -1)) { fprintf(stderr, "*demux: Missing suboptions\n"); exit(1); } if((stream_nr < 0) && (stream_nr > 0xf)) { fprintf(stderr, "*demux: Invalid stream nr\n"); exit(1); } stream_id = (0xc0 | stream_nr); if(file != NULL) { audio_file = fopen(file,"w"); if(!audio_file) { perror(optarg); exit(1); } id_add(stream_id, 0, STREAM_DECODE, -1, NULL, audio_file); } else { fprintf(stderr, "Audio stream %d disabled\n", stream_nr); id_add(stream_id, 0, STREAM_DISCARD, -1, NULL, NULL); } break; case 's': stream_nr = -1; file = NULL; options = optarg; while (*options != '\0') { switch(getsubopt(&options, stream_opts, &opt_value)) { case OPT_STREAM_NR: if(opt_value == NULL) { exit(1); } stream_nr = atoi(opt_value); break; case OPT_FILE: if(opt_value == NULL) { exit(1); } file = opt_value; break; default: fprintf(stderr, "*demux: Unknown suboption: %s\n", options); exit(1); break; } } if((stream_nr == -1)) { fprintf(stderr, "*demux: Missing suboptions\n"); exit(1); } if((stream_nr < 0) && (stream_nr > 0x1f)) { fprintf(stderr, "*demux: Invalid stream nr\n"); exit(1); } stream_id = (0x20 | stream_nr); if(file != NULL) { subtitle_file = fopen(file,"w"); if(!subtitle_file) { perror(optarg); exit(1); } id_add(MPEG2_PRIVATE_STREAM_1, stream_id, STREAM_DECODE, -1, NULL, subtitle_file); } else { fprintf(stderr, "Subtitle stream %d disabled\n", stream_nr); id_add(MPEG2_PRIVATE_STREAM_1, stream_id, STREAM_DISCARD, -1, NULL, NULL); } break; case 'd': debug = atoi(optarg); break; case 'm': msgqid = atoi(optarg); break; case 'o': offs = atoi(optarg); break; case 'h': case '?': usage(); return 1; } } if(msgqid == -1) { if(argc - optind != 1){ usage(); return 1; } } if(msgqid != -1) { MsgEvent_t regev; int fileopen = 0; init_id_reg(STREAM_DISCARD); // get a handle if((msgq = MsgOpen(msgqid)) == NULL) { FATAL("%s", "Couldn't get message q\n"); exit(1); }#if DEBUG fprintf(stderr, "demux: msgq opened, clientnr: %ld\n", msgq->mtype);#endif // register with the resource manager and tell what we can do regev.type = MsgEventQRegister; regev.registercaps.capabilities = DEMUX_MPEG1 | DEMUX_MPEG2_PS; if(MsgSendEvent(msgq, CLIENT_RESOURCE_MANAGER, ®ev, 0) == -1) { fprintf(stderr, "demux: register\n"); }#if DEBUG fprintf(stderr, "demux: sent register\n");#endif /* wait for load_file command */ //get_next_demux_q(); while(!fileopen) { if(MsgNextEvent(msgq, ®ev) != -1) { switch(regev.type) { case MsgEventQChangeFile:#if DEBUG fprintf(stderr, "demux: got changefile\n");#endif loadinputfile(regev.changefile.filename); fileopen = 1; break; case MsgEventQCtrlData:#if DEBUG fprintf(stderr, "demux: got ctrldata\n");#endif attach_ctrl_shm(regev.ctrldata.shmid); break; case MsgEventQDemuxDVDRoot:#if DEBUG fprintf(stderr, "demux: got dvd root\n");#endif handle_events(®ev); fileopen = 1; break; default: handle_events(®ev); /* fprintf(stderr, "demux: msg not wanted %d, from %ld\n", regev.type, regev.any.client); */ break; } } } //fprintf(stderr, "demux: file opened\n"); get_buffer(4*1024*1024); } else { loadinputfile(argv[optind]); } // Setup signal handler for SEGV, to detect that we ran // out of file without a test. sig.sa_handler = segvhandler; sig.sa_flags = 0; rv = sigaction(SIGSEGV, &sig, NULL); if(rv == -1) { perror("*demux: sighandler"); exit(1); } #if DEBUG fprintf(stderr, "demux: get next demux q\n");#endif if(msgqid != -1) { get_next_demux_q(); } if(off_from != -1) { //fprintf(stderr, "demux: off_from pack\n"); offs = off_from; bits_left = 64; off_from = -1; GETBITS(32, "skip1"); GETBITS(32, "skip2"); } else { fprintf(stderr, "*demux: internal error1\n"); exit(1); } while(1) { // fprintf(stderr, "Searching for Program Stream\n"); if(nextbits(32) == MPEG2_PS_PACK_START_CODE) { if(!synced) { synced = 1;#if DEBUG fprintf(stderr, "demux: Found Program Stream\n");#endif } MPEG2_program_stream(); lost_sync = 1; } else if(nextbits(32) == MPEG2_VS_SEQUENCE_HEADER_CODE) { fprintf(stderr, "demux: Found Video Sequence Header, " "seems to be an Elementary Stream (video)\n"); lost_sync = 1; } GETBITS(8, "resync"); DPRINTF(1, "resyncing"); if(lost_sync) { lost_sync = 0; WARNING("%s", "Lost sync, resyncing\n"); } }}static void handle_events(MsgEvent_t *ev){ switch(ev->type) { case MsgEventQNotify: DPRINTF(1, "demux: got notify\n"); break; case MsgEventQChangeFile: DPRINTF(1, "demux: change file: %s\n", ev->changefile.filename); add_to_demux_q(ev); break; case MsgEventQGntStreamBuf: DPRINTF(1, "demux: got stream %x, %x buffer \n", ev->gntstreambuf.stream_id, ev->gntstreambuf.subtype); attach_decoder_buffer(ev->gntstreambuf.stream_id, ev->gntstreambuf.subtype, ev->gntstreambuf.q_shmid); break; case MsgEventQPlayCtrl: add_to_demux_q(ev); break; case MsgEventQDemuxStream: if(ev->demuxstream.stream_id != MPEG2_PRIVATE_STREAM_1) { id_reg[ev->demuxstream.stream_id].state = STREAM_DECODE; } else { id_reg_ps1[ev->demuxstream.subtype].state = STREAM_DECODE; } break; case MsgEventQDemuxStreamChange: switch_to_stream(ev->demuxstream.stream_id, ev->demuxstream.subtype); break; case MsgEventQDemuxStreamChange2: switch_from_to_stream(ev->demuxstreamchange2.old_stream_id, ev->demuxstreamchange2.old_subtype, ev->demuxstreamchange2.new_stream_id, ev->demuxstreamchange2.new_subtype); break; case MsgEventQDemuxDefault: init_id_reg(ev->demuxdefault.state); break; case MsgEventQDemuxDVD: add_to_demux_q(ev); break; case MsgEventQDemuxDVDRoot: add_to_demux_q(ev); break; default:#if DEBUG fprintf(stderr, "demux: unrecognized command: %d\n", ev->type);#endif break; }}int register_id(uint8_t id, int subtype){ MsgEvent_t ev; data_buf_head_t *data_buf_head; int qsize; if(msgqid != -1) {
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -