X-Git-Url: https://asedeno.scripts.mit.edu/gitweb/?a=blobdiff_plain;f=misc.c;h=b4fff66655b843922c781b28ae625f454113ede9;hb=6f6e9db932589470975ecc23261cd57eb9e710be;hp=054b7938be1573481fa045ebe211e5fa654fdb4b;hpb=b599e77ada8399459b14c710ed1db1e48456c868;p=PuTTY.git diff --git a/misc.c b/misc.c index 054b7938..b4fff666 100644 --- a/misc.c +++ b/misc.c @@ -208,6 +208,29 @@ void burnstr(char *string) /* sfree(str), only clear it first */ } } +int toint(unsigned u) +{ + /* + * Convert an unsigned to an int, without running into the + * undefined behaviour which happens by the strict C standard if + * the value overflows. You'd hope that sensible compilers would + * do the sensible thing in response to a cast, but actually I + * don't trust modern compilers not to do silly things like + * assuming that _obviously_ you wouldn't have caused an overflow + * and so they can elide an 'if (i < 0)' test immediately after + * the cast. + * + * Sensible compilers ought of course to optimise this entire + * function into 'just return the input value'! + */ + if (u <= (unsigned)INT_MAX) + return (int)u; + else if (u >= (unsigned)INT_MIN) /* wrap in cast _to_ unsigned is OK */ + return INT_MIN + (int)(u - (unsigned)INT_MIN); + else + return INT_MIN; /* fallback; should never occur on binary machines */ +} + /* * Do an sprintf(), but into a custom-allocated buffer. *