X-Git-Url: https://git.ucc.asn.au/?a=blobdiff_plain;f=Kernel%2Flib.c;h=28edc5617e63f35c434e2aaebadce162d4f721ba;hb=327c86d2221d49994ad49ec0d1717444e04521b8;hp=3e57d00d721800551bef3568428482a4ec8f4916;hpb=9d85201216cb35e1b1e051b1d7cdc38eaa5befa4;p=tpg%2Facess2.git diff --git a/Kernel/lib.c b/Kernel/lib.c index 3e57d00d..28edc561 100644 --- a/Kernel/lib.c +++ b/Kernel/lib.c @@ -62,6 +62,8 @@ EXPORT(ByteSum); EXPORT(strlen); EXPORT(strcpy); EXPORT(strncpy); +EXPORT(strcat); +EXPORT(strncat); EXPORT(strcmp); EXPORT(strncmp); //EXPORT(strdup); @@ -77,6 +79,8 @@ EXPORT(CheckMem); EXPORT(ModUtil_LookupString); EXPORT(ModUtil_SetIdent); EXPORT(UnHex); +EXPORT(SwapEndian16); +EXPORT(SwapEndian32); // === CODE === /** @@ -155,6 +159,7 @@ void itoa(char *buf, Uint64 num, int base, int minLength, char pad) { char tmpBuf[64+1]; int pos=0, i; + Uint64 rem; // Sanity check if(!buf) return; @@ -167,11 +172,11 @@ void itoa(char *buf, Uint64 num, int base, int minLength, char pad) // Convert while(num > base-1) { - tmpBuf[pos] = cUCDIGITS[ num % base ]; - num /= (Uint)base; // Shift `num` right 1 digit + num = DivMod64U(num, base, &rem); // Shift `num` and get remainder + tmpBuf[pos] = cUCDIGITS[ rem ]; pos++; } - tmpBuf[pos++] = cUCDIGITS[ num % base ]; // Last digit of `num` + tmpBuf[pos++] = cUCDIGITS[ num ]; // Last digit of `num` // Put in reverse i = 0; @@ -199,7 +204,7 @@ void itoa(char *buf, Uint64 num, int base, int minLength, char pad) int vsnprintf(char *__s, size_t __maxlen, const char *__format, va_list args) { char c, pad = ' '; - int minSize = 0, len; + int minSize = 0, precision = -1, len; char tmpBuf[34]; // For Integers const char *p = NULL; int isLongLong = 0; @@ -231,7 +236,7 @@ int vsnprintf(char *__s, size_t __maxlen, const char *__format, va_list args) } // - Padding Side Flag - if(c == '+') { + if(c == '-') { bPadLeft = 1; c = *__format++; } @@ -260,7 +265,28 @@ int vsnprintf(char *__s, size_t __maxlen, const char *__format, va_list args) } } else - minSize = 1; + minSize = 0; + + // - Precision + precision = -1; + if( c == '.' ) { + c = *__format++; + + if(c == '*') { // Dynamic length + precision = va_arg(args, unsigned int); + c = *__format++; + } + else if('1' <= c && c <= '9') + { + precision = 0; + while('0' <= c && c <= '9') + { + precision *= 10; + precision += c - '0'; + c = *__format++; + } + } + } // - Default, Long or LongLong? isLongLong = 0; @@ -290,22 +316,29 @@ int vsnprintf(char *__s, size_t __maxlen, const char *__format, va_list args) } itoa(tmpBuf, val, 10, minSize, pad); goto printString; - case 'u': + case 'u': // Unsigned GETVAL(); itoa(tmpBuf, val, 10, minSize, pad); goto printString; - case 'X': + case 'P': // Physical Address + PUTCH('0'); + PUTCH('x'); + if(sizeof(tPAddr) > 4) isLongLong = 1; + GETVAL(); + itoa(tmpBuf, val, 16, minSize, pad); + goto printString; + case 'X': // Hex if(BITS == 64) isLongLong = 1; // TODO: Handle non-x86 64-bit archs GETVAL(); itoa(tmpBuf, val, 16, minSize, pad); goto printString; - case 'x': + case 'x': // Lower case hex GETVAL(); itoa(tmpBuf, val, 16, minSize, pad); goto printString; - case 'o': + case 'o': // Octal GETVAL(); itoa(tmpBuf, val, 8, minSize, pad); goto printString; @@ -323,12 +356,12 @@ int vsnprintf(char *__s, size_t __maxlen, const char *__format, va_list args) // String - Null Terminated Array case 's': p = va_arg(args, char*); // Get Argument - if( !CheckString(p) ) continue; // Avoid #PFs + if( !CheckString(p) ) p = "(inval)"; // Avoid #PFs printString: if(!p) p = "(null)"; len = strlen(p); if( !bPadLeft ) while(len++ < minSize) PUTCH(pad); - while(*p) PUTCH(*p++); + while(*p && precision--) PUTCH(*p++); if( bPadLeft ) while(len++ < minSize) PUTCH(pad); break; @@ -441,7 +474,6 @@ size_t strlen(const char *__str) } /** - * \fn char *strcpy(char *__str1, const char *__str2) * \brief Copy a string to a new location */ char *strcpy(char *__str1, const char *__str2) @@ -453,8 +485,8 @@ char *strcpy(char *__str1, const char *__str2) } /** - * \fn char *strncpy(char *__str1, const char *__str2, size_t max) * \brief Copy a string to a new location + * \note Copies at most `max` chars */ char *strncpy(char *__str1, const char *__str2, size_t max) { @@ -465,6 +497,32 @@ char *strncpy(char *__str1, const char *__str2, size_t max) return __str1; } +/** + * \brief Append a string to another + */ +char *strcat(char *__dest, const char *__src) +{ + while(*__dest++); + __dest--; + while(*__src) + *__dest++ = *__src++; + *__dest = '\0'; + return __dest; +} + +/** + * \brief Append at most \a n chars to a string from another + * \note At most n+1 chars are written (the dest is always zero terminated) + */ +char *strncat(char *__dest, const char *__src, size_t n) +{ + while(*__dest++); + while(*__src && n-- >= 1) + *__dest++ = *__src++; + *__dest = '\0'; + return __dest; +} + /** * \fn int strcmp(const char *str1, const char *str2) * \brief Compare two strings return the difference between @@ -851,7 +909,7 @@ int ModUtil_SetIdent(char *Dest, const char *Value) /** * \brief Convert a string of hexadecimal digits into a byte stream */ -int UnHex(Uint8 *Dest, size_t DestSize, const char *SourceString) +int UnHex(Uint8 *Dest, size_t DestSize, const char *SourceString) { int i; @@ -881,3 +939,12 @@ int UnHex(Uint8 *Dest, size_t DestSize, const char *SourceString) } return i/2; } + +Uint16 SwapEndian16(Uint16 Val) +{ + return ((Val&0xFF)<<8) | ((Val>>8)&0xFF); +} +Uint32 SwapEndian32(Uint32 Val) +{ + return ((Val&0xFF)<<24) | ((Val&0xFF00)<<8) | ((Val>>8)&0xFF00) | ((Val>>24)&0xFF); +}