diff --git a/hmml_to_html/hmml_to_html.c b/hmml_to_html/hmml_to_html.c index 5983101..4ef0b44 100644 --- a/hmml_to_html/hmml_to_html.c +++ b/hmml_to_html/hmml_to_html.c @@ -127,81 +127,25 @@ category_medium CategoryMedium[] = #define ArrayCount(A) sizeof(A)/sizeof(*(A)) -#define ClaimBuffer(MemoryArena, ClaimedMemory, Buffer, ID, Size) if(__ClaimBuffer(MemoryArena, ClaimedMemory, Buffer, ID, Size))\ -{\ - fprintf(stderr, "%s:%d: MemoryArena cannot contain %s of size %d\n", __FILE__, __LINE__, ID, Size);\ - hmml_free(&HMML);\ - FreeBuffer(MemoryArena);\ - return 1;\ -}; - +__attribute__ ((format (printf, 2, 3))) void -FreeBuffer(buffer *Buffer) +CopyString(char Dest[], char *Format, ...) { - free(Buffer->Location); + va_list Args; + va_start(Args, Format); + vsprintf(Dest, Format, Args); + va_end(Args); } int -__ClaimBuffer(buffer *MemoryArena, int *ClaimedMemory, buffer *Buffer, char *ID, int Size) +StringLength(char *String) { - if(*ClaimedMemory + Size > MemoryArena->Size) + int i = 0; + while(String[i]) { - return 1; + ++i; } - Buffer->Location = MemoryArena->Location + *ClaimedMemory; - Buffer->Size = Size; - Buffer->ID = ID; - *ClaimedMemory += Buffer->Size; - *Buffer->Location = '\0'; - Buffer->Ptr = Buffer->Location; -#if DEBUG - printf(" Claimed: %s: %d\n" - " Total ClaimedMemory: %d\n\n", Buffer->ID, Buffer->Size, *ClaimedMemory); -#endif - return 0; -} - -void -DeclaimBuffer(buffer *Buffer, int *ClaimedMemory) -{ - *Buffer->Location = '\0'; - *ClaimedMemory -= Buffer->Size; -#if DEBUG - printf("Declaimed: %s\n" - " Total ClaimedMemory: %d\n\n", Buffer->ID, *ClaimedMemory); -#endif -} - -int -TimecodeToSeconds(char *Timecode) -{ - int HMS[3] = { 0, 0, 0 }; // 0 == Seconds; 1 == Minutes; 2 == Hours - int Colons = 0; - while(*Timecode) - { - //if((*Timecode < '0' || *Timecode > '9') && *Timecode != ':') { return FALSE; } - - if(*Timecode == ':') - { - ++Colons; - //if(Colons > 2) { return FALSE; } - for(int i = 0; i < Colons; ++i) - { - HMS[Colons - i] = HMS[Colons - (i + 1)]; - } - HMS[0] = 0; - } - else - { - HMS[0] = HMS[0] * 10 + *Timecode - '0'; - } - - ++Timecode; - } - - //if(HMS[0] > 59 || HMS[1] > 59 || Timecode[-1] == ':') { return FALSE; } - - return HMS[2] * 60 * 60 + HMS[1] * 60 + HMS[0]; + return i; } void @@ -223,16 +167,6 @@ CopyBuffer(buffer *Dest, buffer *Src) *Dest->Ptr = '\0'; } -__attribute__ ((format (printf, 2, 3))) -void -CopyString(char Dest[], char *Format, ...) -{ - va_list Args; - va_start(Args, Format); - vsprintf(Dest, Format, Args); - va_end(Args); -} - int CopyStringNoFormat(char *Dest, char *String) { @@ -259,17 +193,6 @@ CopyStringNoFormatT(char *Dest, char *String, char Terminator) return Length; } -int -StringLength(char *String) -{ - int i = 0; - while(String[i]) - { - ++i; - } - return i; -} - __attribute__ ((format (printf, 2, 3))) void CopyStringToBuffer(buffer *Dest, char *Format, ...) @@ -402,6 +325,153 @@ StringsDifferT(char *A, // NOTE(matt): Null-terminated string } } +int +MakeDir(char *Path) +{ + int i = StringLength(Path); + int Ancestors = 0; + while(mkdir(Path, 00755) == -1) + { + while(Path[i] != '/' && i > 0) + { + --i; + } + ++Ancestors; + Path[i] = '\0'; + if(i == 0) { return 1; } + } + while(Ancestors > 0) + { + while(Path[i] != '\0') + { + ++i; + } + Path[i] = '/'; + --Ancestors; + if((mkdir(Path, 00755)) == -1) + { + return 1; + } + } + return 0; +} + +void +FreeBuffer(buffer *Buffer) +{ + free(Buffer->Location); +} + +#define ClaimBuffer(MemoryArena, ClaimedMemory, Buffer, ID, Size) if(__ClaimBuffer(MemoryArena, ClaimedMemory, Buffer, ID, Size))\ +{\ + fprintf(stderr, "%s:%d: MemoryArena cannot contain %s of size %d\n", __FILE__, __LINE__, ID, Size);\ + hmml_free(&HMML);\ + FreeBuffer(MemoryArena);\ + return 1;\ +}; + +int +__ClaimBuffer(buffer *MemoryArena, int *ClaimedMemory, buffer *Buffer, char *ID, int Size) +{ + if(*ClaimedMemory + Size > MemoryArena->Size) + { + return 1; + } + Buffer->Location = MemoryArena->Location + *ClaimedMemory; + Buffer->Size = Size; + Buffer->ID = ID; + *ClaimedMemory += Buffer->Size; + *Buffer->Location = '\0'; + Buffer->Ptr = Buffer->Location; +#if DEBUG + printf(" Claimed: %s: %d\n" + " Total ClaimedMemory: %d\n\n", Buffer->ID, Buffer->Size, *ClaimedMemory); +#endif + return 0; +} + +void +LogUsage(buffer Buffer, char *CacheDir) +{ + char LogPath[255]; + CopyString(LogPath, "%s/%s", CacheDir, "buffers.log"); + FILE *LogFile; + if(!(LogFile = fopen(LogPath, "a+"))) + { + MakeDir(CacheDir); + if(!(LogFile = fopen(LogPath, "a+"))) + { + perror("LogUsage"); + return; + } + } + + fprintf(LogFile, "%s,%ld,%d\n", + Buffer.ID, + Buffer.Ptr - Buffer.Location, + Buffer.Size); + fclose(LogFile); +} + +#define DeclaimBuffer(Buffer, ClaimedMemory) __DeclaimBuffer(Buffer, ClaimedMemory, CacheDir) + +void +__DeclaimBuffer(buffer *Buffer, int *ClaimedMemory, char *CacheDir) +{ + *Buffer->Location = '\0'; + *ClaimedMemory -= Buffer->Size; + float PercentageUsed = (float)(Buffer->Ptr - Buffer->Location) / Buffer->Size * 100; +#if DEBUG + printf("Declaimed: %s\n" + " Used: %ld / %d (%.2f%%)\n" + "\n" + " Total ClaimedMemory: %d\n\n", + Buffer->ID, + Buffer->Ptr - Buffer->Location, + Buffer->Size, + PercentageUsed, + *ClaimedMemory); +#endif + LogUsage(*Buffer, CacheDir); + if(PercentageUsed >= 80.0f) + { + // TODO(matt): Implement either dynamically growing buffers, or phoning home to matt@handmadedev.org + fprintf(stderr, "Warning: %s used %.2f%% of its allotted memory\n", Buffer->ID, PercentageUsed); + } +} + +int +TimecodeToSeconds(char *Timecode) +{ + int HMS[3] = { 0, 0, 0 }; // 0 == Seconds; 1 == Minutes; 2 == Hours + int Colons = 0; + while(*Timecode) + { + //if((*Timecode < '0' || *Timecode > '9') && *Timecode != ':') { return FALSE; } + + if(*Timecode == ':') + { + ++Colons; + //if(Colons > 2) { return FALSE; } + for(int i = 0; i < Colons; ++i) + { + HMS[Colons - i] = HMS[Colons - (i + 1)]; + } + HMS[0] = 0; + } + else + { + HMS[0] = HMS[0] * 10 + *Timecode - '0'; + } + + ++Timecode; + } + + //if(HMS[0] > 59 || HMS[1] > 59 || Timecode[-1] == ':') { return FALSE; } + + return HMS[2] * 60 * 60 + HMS[1] * 60 + HMS[0]; +} + typedef struct { unsigned int Hue:16; @@ -853,37 +923,6 @@ StringToInt(char *String) return Result; } -int -MakeDir(char *Path) -{ - int i = StringLength(Path); - int Ancestors = 0; - while(mkdir(Path, 00755) == -1) - { - while(Path[i] != '/' && i > 0) - { - --i; - } - ++Ancestors; - Path[i] = '\0'; - if(i == 0) { return 1; } - } - while(Ancestors > 0) - { - while(Path[i] != '\0') - { - ++i; - } - Path[i] = '/'; - --Ancestors; - if((mkdir(Path, 00755)) == -1) - { - return 1; - } - } - return 0; -} - size_t CurlIntoBuffer(char *InPtr, size_t CharLength, size_t Chars, char **OutputPtr) { @@ -1052,7 +1091,7 @@ BuildQuote(quote_info *Info, char *Speaker, int ID, char *CacheDir) } void -GenerateTopicColours(buffer *Colour, char *Topic, char *TopicsDir) +GenerateTopicColours(char *Topic, char *TopicsDir) { for(int i = 0; i < ArrayCount(CategoryMedium); ++i) { @@ -1759,7 +1798,6 @@ main(int ArgC, char **Args) // FilterMedia // CreditsMenu // Player - // Colour // Annotation // AnnotationHeader // AnnotationClass @@ -1781,7 +1819,6 @@ main(int ArgC, char **Args) buffer CreditsMenu; buffer Player; - buffer Colour; buffer Annotation; buffer AnnotationHeader; buffer AnnotationClass; @@ -1830,8 +1867,6 @@ main(int ArgC, char **Args) // FilterMedia // CreditsMenu // Player - // Colour - // Annotation // Script // FilterState @@ -1847,8 +1882,6 @@ main(int ArgC, char **Args) ClaimBuffer(&MemoryArena, &ClaimedMemory, &CreditsMenu, "CreditsMenu", Kilobytes(8)); ClaimBuffer(&MemoryArena, &ClaimedMemory, &Player, "Player", Kilobytes(256)); - ClaimBuffer(&MemoryArena, &ClaimedMemory, &Colour, "Colour", 32); - ClaimBuffer(&MemoryArena, &ClaimedMemory, &Annotation, "Annotation", Kilobytes(8)); ClaimBuffer(&MemoryArena, &ClaimedMemory, &Script, "Script", Kilobytes(8)); ClaimBuffer(&MemoryArena, &ClaimedMemory, &FilterState, "FilterState", Kilobytes(4)); @@ -1914,12 +1947,14 @@ goto Cleanup; quote_info QuoteInfo = { 0 }; // NOTE(matt): Tree structure of "annotation local" buffer dependencies - // AnnotationHeader - // AnnotationClass - // AnnotationData - // Text - // TopicDots + // Annotation + // AnnotationHeader + // AnnotationClass + // AnnotationData + // Text + // TopicDots + ClaimBuffer(&MemoryArena, &ClaimedMemory, &Annotation, "Annotation", Kilobytes(8)); ClaimBuffer(&MemoryArena, &ClaimedMemory, &AnnotationHeader, "AnnotationHeader", 512); ClaimBuffer(&MemoryArena, &ClaimedMemory, &AnnotationClass, "AnnotationClass", 256); ClaimBuffer(&MemoryArena, &ClaimedMemory, &AnnotationData, "AnnotationData", 512); @@ -2031,7 +2066,7 @@ goto Cleanup; } else if(Anno->markers[MarkerIndex].type == HMML_CATEGORY) { - GenerateTopicColours(&Colour, Anno->markers[MarkerIndex].marker, CSSDir); + GenerateTopicColours(Anno->markers[MarkerIndex].marker, CSSDir); if(!HasFilterMenu) { HasFilterMenu = TRUE; @@ -2293,7 +2328,7 @@ goto Cleanup; while(MarkerIndex < Anno->marker_count) { - GenerateTopicColours(&Colour, Anno->markers[MarkerIndex].marker, CSSDir); + GenerateTopicColours(Anno->markers[MarkerIndex].marker, CSSDir); if(!HasFilterMenu) { HasFilterMenu = TRUE; @@ -2356,18 +2391,19 @@ goto Cleanup; CopyBuffer(&Player, &Annotation); // NOTE(matt): Tree structure of "annotation local" buffer dependencies - // TopicDots - // Text - // AnnotationData - // AnnotationClass - // AnnotationHeader + // TopicDots + // Text + // AnnotationData + // AnnotationClass + // AnnotationHeader + // Annotation DeclaimBuffer(&TopicDots, &ClaimedMemory); DeclaimBuffer(&Text, &ClaimedMemory); DeclaimBuffer(&AnnotationData, &ClaimedMemory); DeclaimBuffer(&AnnotationClass, &ClaimedMemory); DeclaimBuffer(&AnnotationHeader, &ClaimedMemory); - Annotation.Ptr = Annotation.Location; + DeclaimBuffer(&Annotation, &ClaimedMemory); } #if DEBUG @@ -3193,26 +3229,22 @@ goto Cleanup; } // NOTE(matt): Tree structure of "global" buffer dependencies - // FilterState - // Script - // Annotation - // Colour - // Player - // CreditsMenu - // FilterMedia - // FilterTopics - // FilterMenu - // ReferenceMenu - // QuoteMenu - // Menus + // FilterState + // Script + // Player + // CreditsMenu + // FilterMedia + // FilterTopics + // FilterMenu + // ReferenceMenu + // QuoteMenu + // Menus // Includes // Master Cleanup: DeclaimBuffer(&FilterState, &ClaimedMemory); DeclaimBuffer(&Script, &ClaimedMemory); - DeclaimBuffer(&Annotation, &ClaimedMemory); - DeclaimBuffer(&Colour, &ClaimedMemory); DeclaimBuffer(&Player, &ClaimedMemory); DeclaimBuffer(&CreditsMenu, &ClaimedMemory);