Changeset 1000

Show
Ignore:
Timestamp:
12/19/08 19:27:50 (1 year ago)
Author:
gbooker
Message:
  • Added field to ExtractVobSubPacket? to figure return the amount of data used from the source as well as return the extracted size
  • Corrected idx/sub parser to handle a wider variety of cases and not crash
Files:

Legend:

Unmodified
Added
Removed
Modified
Copied
Moved
  • trunk/Subtitles/SubImport.mm

    r982 r1000  
    1818 
    1919extern "C" { 
    20         void ExtractVobSubPacket(UInt8 *dest, const UInt8 *framedSrc, int srcSize); 
     20        int ExtractVobSubPacket(UInt8 *dest, const UInt8 *framedSrc, int srcSize, int *usedSrcBytes); 
    2121} 
    2222 
     
    753753        {        
    754754                uint8_t *controlSeq = packet + controlOffset; 
    755                 uint32_t i = 4, end = length - controlOffset; 
     755                int32_t i = 4; 
     756                int32_t end = length - controlOffset; 
    756757                uint16_t timestamp = (controlSeq[0] << 8) | controlSeq[1]; 
    757758                uint16_t nextOffset = (controlSeq[2] << 8) + controlSeq[3]; 
     
    799800                                                loop = false; 
    800801                                        controlOffset = nextOffset; 
    801                                         i = end
     802                                        i = 0x7fffffff
    802803                                        break; 
    803804                                         
     
    808809                        } 
    809810                } 
     811                if(i != 0x7fffffff) 
     812                { 
     813                        //End of packet 
     814                        loop = false; 
     815                } 
    810816        } 
    811817}        
     
    830836         
    831837        VobSubState state = VOB_SUB_STATE_READING_PRIVATE; 
    832         VobSubTrack *currentTrack = nil, *lastTrack = nil; 
    833         long movieDuration = (GetMovieDuration(theMovie) * 1000 / GetMovieTimeScale(theMovie)); 
     838        VobSubTrack *currentTrack = nil; 
    834839        int imageWidth = 0, imageHeight = 0; 
    835840        long delay=0; 
     
    841846        if(![idxContent length]) 
    842847                goto bail; 
     848         
     849        int subFileSize = [[[[NSFileManager defaultManager] fileAttributesAtPath:subFileName traverseLink:NO] objectForKey:NSFileSize] intValue]; 
    843850         
    844851        NSArray *lines = [idxContent componentsSeparatedByString:@"\n"]; 
     
    889896                                        NSString *language = [NSString stringWithUTF8String:langStr]; 
    890897                                         
    891                                         lastTrack = currentTrack; 
    892898                                        currentTrack = [[VobSubTrack alloc] initWithPrivateData:privateData language:language andIndex:index]; 
    893899                                        [tracks addObject:currentTrack]; 
     
    905911                                long time = scanTime(timeStr); 
    906912                                free(timeStr); 
    907                                 if(lastTrack) 
    908                                 { 
    909                                         [lastTrack addSampleTime:movieDuration offset:position]; 
    910                                         lastTrack = nil; 
    911                                 } 
    912913                                [currentTrack addSampleTime:time + delay offset:position]; 
    913914                        } 
     
    915916                } 
    916917        } 
    917         if(lastTrack) 
    918         { 
    919                 int position = [[[[NSFileManager defaultManager] fileAttributesAtPath:subFileName traverseLink:NO] objectForKey:NSFileSize] intValue]; 
    920                 [lastTrack addSampleTime:movieDuration offset:position]; 
    921         } 
    922          
     918                 
    923919        if([tracks count]) 
    924920        { 
     
    947943                        } 
    948944                         
    949                         int sampleCount = [track->samples count] - 1
     945                        int sampleCount = [track->samples count]
    950946                        int totalSamples = sampleCount; 
    951947                        SampleReference64Ptr samples = (SampleReference64Ptr)calloc(sampleCount*2, sizeof(SampleReference64Record)); 
    952948                        SampleReference64Ptr sample = samples; 
    953                         VobSubSample *lastSample = [track->samples objectAtIndex:0]; 
    954949                        int i; 
    955950                        uint32_t lastTime = 0; 
    956951                        for(i=0; i<sampleCount; i++) 
    957952                        { 
    958                                 VobSubSample *nextSample = [track->samples objectAtIndex:i+1]; 
    959                                 int offset = lastSample->fileOffset; 
    960                                 int size = nextSample->fileOffset - offset; 
     953                                VobSubSample *currentSample = [track->samples objectAtIndex:i]; 
     954                                int offset = currentSample->fileOffset; 
     955                                int nextOffset; 
     956                                if(i == sampleCount - 1) 
     957                                        nextOffset = subFileSize; 
     958                                else 
     959                                        nextOffset = ((VobSubSample *)[track->samples objectAtIndex:i+1])->fileOffset; 
     960                                int size = nextOffset - offset; 
     961                                if(size < 0) 
     962                                        //Skip samples for which we cannot determine size 
     963                                        continue; 
    961964                                 
    962965                                NSData *subData = [subFileData subdataWithRange:NSMakeRange(offset, size)]; 
    963966                                uint8_t *extracted = (uint8_t *)malloc(size); 
    964                                 ExtractVobSubPacket(extracted, (const UInt8 *)[subData bytes], size); 
     967                                int extractedSize = ExtractVobSubPacket(extracted, (const UInt8 *)[subData bytes], size, &size); 
    965968                                 
    966969                                uint16_t startTimestamp, endTimestamp; 
    967                                 ReadPacketTimes(extracted, size, &startTimestamp, &endTimestamp); 
     970                                ReadPacketTimes(extracted, extractedSize, &startTimestamp, &endTimestamp); 
    968971                                free(extracted); 
    969                                 uint32_t startTime = lastSample->timeStamp + startTimestamp; 
    970                                 uint32_t endTime = lastSample->timeStamp + endTimestamp; 
     972                                uint32_t startTime = currentSample->timeStamp + startTimestamp; 
     973                                uint32_t endTime = currentSample->timeStamp + endTimestamp; 
     974                                int duration = endTimestamp - startTimestamp; 
     975                                if(duration <= 0) 
     976                                        //Skip samples which are broken 
     977                                        continue; 
    971978                                if(i == 0) 
    972                                         lastSample->timeStamp = startTime; 
     979                                        currentSample->timeStamp = startTime; 
    973980                                else if(lastTime != startTime) 
    974981                                { 
     
    984991                                sample->dataOffset.hi = 0; 
    985992                                sample->dataOffset.lo = offset; 
    986                                 sample->dataSize = nextSample->fileOffset - lastSample->fileOffset
     993                                sample->dataSize = size
    987994                                sample->sampleFlags = 0; 
    988                                 sample->durationPerSample = endTimestamp - startTimestamp
     995                                sample->durationPerSample = duration
    989996                                sample->numberOfSamples = 1; 
    990997                                lastTime = endTime; 
    991998                                 
    992                                 lastSample = nextSample; 
    993999                                sample++; 
    9941000                        } 
  • trunk/VobSubCodec.c

    r982 r1000  
    6262 
    6363// dest must be at least as large as src 
    64 void ExtractVobSubPacket(UInt8 *dest, UInt8 *framedSrc, int srcSize); 
     64int ExtractVobSubPacket(UInt8 *dest, UInt8 *framedSrc, int srcSize, int *usedSrcBytes); 
    6565static ComponentResult ReadPacketControls(UInt8 *packet, UInt32 palette[16], PacketControlData *controlDataOut); 
    6666extern void initLib(); 
     
    308308        } else if (data[0] + data[1] == 0) { 
    309309                // remove the MPEG framing 
    310                 ExtractVobSubPacket(glob->codecData, data, myDrp->bufferSize); 
     310                myDrp->bufferSize = ExtractVobSubPacket(glob->codecData, data, myDrp->bufferSize, NULL); 
    311311        } else { 
    312312                memcpy(glob->codecData, drp->codecData, myDrp->bufferSize); 
     
    414414} 
    415415 
    416 void ExtractVobSubPacket(UInt8 *dest, UInt8 *framedSrc, int srcSize) { 
     416int ExtractVobSubPacket(UInt8 *dest, UInt8 *framedSrc, int srcSize, int *usedSrcBytes) { 
    417417        int copiedBytes = 0; 
    418418        UInt8 *currentPacket = framedSrc; 
    419          
    420         while (currentPacket - framedSrc < srcSize) { 
     419        int packetSize = 0x7fffffff; 
     420         
     421        while (currentPacket - framedSrc < srcSize && copiedBytes < packetSize) { 
    421422                // 3-byte start code: 0x00 00 01 
    422423                if (currentPacket[0] + currentPacket[1] != 0 || currentPacket[2] != 1) { 
    423424                        Codecprintf(NULL, "VobSub Codec: !! Unknown header: %02x %02x %02x\n", currentPacket[0], currentPacket[1], currentPacket[2]); 
    424                         return
     425                        return copiedBytes
    425426                } 
    426427                 
     
    461462                                           packet_length - 1 - (header_data_length + 3)); 
    462463                                 
     464                                if(packetSize == 0x7fffffff) 
     465                                { 
     466                                        packetSize = dest[0] << 8 | dest[1]; 
     467                                } 
    463468                                copiedBytes += packet_length - 1 - (header_data_length + 3); 
    464469                                currentPacket += packet_length + 6; 
     
    468473                                // unknown packet, probably video, return for now 
    469474                                Codecprintf(NULL, "VobSubCodec - Unknown packet type %x, aborting\n", (int)currentPacket[3]); 
    470                                 return
     475                                return copiedBytes
    471476                } // switch (currentPacket[3]) 
    472477        } // while (currentPacket - framedSrc < srcSize) 
     478        if(usedSrcBytes != NULL) 
     479                *usedSrcBytes = currentPacket - framedSrc; 
     480         
     481        return copiedBytes; 
    473482} 
    474483