17,100 → 17,6 |
#include "helpers.h" |
|
|
/* translates a version string into a array of integer values. The array must be 8-position long. |
returns 0 if parsing was successful, non-zero otherwise. |
Accepted formats follow: |
300.12.1 |
1 |
12.2.34.2-4.5 |
1.2c |
1.01 |
2013-12-31 */ |
static int versiontointarr(char *verstr, int *arr) { |
int i, vlen, dotcounter = 1, firstcharaftersep = 0; |
char *digits[8]; |
char verstrcopy[16]; |
|
/* fill the array with zeroes first */ |
for (i = 0; i < 8; i++) arr[i] = 0; |
|
/* first extensively validate the input */ |
if (verstr == NULL) return(-1); |
vlen = strlen(verstr); |
if (vlen == 0) return(-1); |
if (vlen > 15) return(-1); |
if ((verstr[0] < '0') || (verstr[0] > '9')) return(-1); /* a version string must start with a 0..9 digit */ |
if ((tolower(verstr[vlen - 1]) >= 'a') && (tolower(verstr[vlen - 1]) <= 'z') && (vlen > 1)) { /* remove any letter from the end, and use it as a (very) minor differenciator */ |
vlen -= 1; |
arr[7] = tolower(verstr[vlen]); |
} |
if ((verstr[vlen - 1] < '0') || (verstr[vlen - 1] > '9')) return(-1); /* a version string must end with a 0..9 digit */ |
|
digits[0] = verstrcopy; |
for (i = 0; i < vlen; i++) { |
verstrcopy[i] = verstr[i]; |
switch (verstr[i]) { |
case '.': |
case '-': |
if (i == 0) return(-1); |
if (verstrcopy[i-1] == 0) return(-1); /* do not allow two separators in a row */ |
if (dotcounter > 6) return(-1); |
digits[dotcounter++] = &verstrcopy[i + 1]; |
verstrcopy[i] = 0; |
firstcharaftersep = 1; |
break; |
case '0': |
/* if this is a zero right after a separator, and trailed with a digit |
* (as in '1.01'), then enforce a separator first */ |
if ((firstcharaftersep != 0) && (verstr[i+1] >= '0') && (verstr[i+1] <= '9')) { |
if (dotcounter > 6) return(-1); |
digits[dotcounter++] = &verstrcopy[i + 1]; |
verstrcopy[i] = 0; |
} |
break; |
case '1': |
case '2': |
case '3': |
case '4': |
case '5': |
case '6': |
case '7': |
case '8': |
case '9': |
firstcharaftersep = 0; |
break; |
default: /* do not allow any character different than 0..9 or '.' */ |
return(-1); |
break; |
} |
} |
verstrcopy[i] = 0; |
/* now that we know the input is sane, let's process it */ |
for (i = 0; i < dotcounter; i++) { |
int tmpint; |
tmpint = atoi(digits[i]); |
if ((tmpint < 0) || (tmpint > 32000)) return(-1); |
arr[i] = tmpint; |
} |
return(0); |
} |
|
|
/* compares version strings v1 and v2. Returns 1 if v2 is newer than v1, 0 otherwise, and -1 if comparison is unable to tell */ |
int isversionnewer(char *v1, char *v2) { |
int x1[8], x2[8], i; |
if ((v1 == NULL) || (v2 == NULL)) return(-1); /* if input is invalid (NULL), don't continue */ |
if (strcasecmp(v1, v2) == 0) return(0); /* if both versions are the same, don't continue */ |
/* check versions of the decimal format 1.23... */ |
if ((versiontointarr(v1, x1) != 0) || (versiontointarr(v2, x2) != 0)) return(-1); |
for (i = 0; i < 8; i++) { |
if (x2[i] > x1[i]) return(1); |
if (x2[i] < x1[i]) return(0); |
} |
return(0); |
} |
|
|
/* change all / to \ in a string */ |
void slash2backslash(char *str) { |
int x; |