From b30a327b31ea0c660d07af56e0d7eec35120d027 Mon Sep 17 00:00:00 2001 From: Matthew Dillon Date: Thu, 7 Jul 2005 07:17:47 +0000 Subject: [PATCH] It is not acceptable to index the array out of bounds if an illegal index is passed to a ctype function or macro. Undo the last commit. Emplace an explicit range check for the integer passed to the ctype macros and functions rather then underflowing or overflowing the array. Currently return 0 if the integer is out of range (it might be more appropriate to assert). --- include/ctype.h | 72 +++++++++++++++++++++++++++--------------- lib/libc/gen/isctype.c | 26 +++++++-------- lib/libc/gen/tolower.c | 4 +-- lib/libc/gen/toupper.c | 4 +-- 4 files changed, 64 insertions(+), 42 deletions(-) diff --git a/include/ctype.h b/include/ctype.h index dabc039aea..ed95f2a0ec 100644 --- a/include/ctype.h +++ b/include/ctype.h @@ -33,7 +33,7 @@ * * @(#)ctype.h 5.3 (Berkeley) 4/3/91 * $NetBSD: src/include/ctype.h,v 1.25 2003/10/22 15:51:18 kleink Exp $ - * $DragonFly: src/include/ctype.h,v 1.13 2005/07/07 05:55:05 joerg Exp $ + * $DragonFly: src/include/ctype.h,v 1.14 2005/07/07 07:17:42 dillon Exp $ */ #ifndef _CTYPE_H_ @@ -86,21 +86,53 @@ int isblank(int); #endif __END_DECLS +#ifdef _CTYPE_PRIVATE +extern const __uint16_t __libc_C_ctype_[]; +extern const __int16_t __libc_C_toupper_[]; +extern const __int16_t __libc_C_tolower_[]; +#endif + +/* + * don't get all wishy washy and try to support architectures where + * char isn't 8 bits. It's 8 bits, period. + */ #if !defined(_CTYPE_H_DISABLE_MACROS_) -#define isdigit(c) ((int)((__libc_ctype_ + 1)[(c)] & _D)) -#define islower(c) ((int)((__libc_ctype_ + 1)[(c)] & _L)) -#define isspace(c) ((int)((__libc_ctype_ + 1)[(c)] & _S)) -#define ispunct(c) ((int)((__libc_ctype_ + 1)[(c)] & _P)) -#define isupper(c) ((int)((__libc_ctype_ + 1)[(c)] & _U)) -#define isalpha(c) ((int)((__libc_ctype_ + 1)[(c)] & _A)) -#define isxdigit(c) ((int)((__libc_ctype_ + 1)[(c)] & _X)) -#define isalnum(c) ((int)((__libc_ctype_ + 1)[(c)] & (_A|_D))) -#define isprint(c) ((int)((__libc_ctype_ + 1)[(c)] & _R)) -#define isgraph(c) ((int)((__libc_ctype_ + 1)[(c)] & _G)) -#define iscntrl(c) ((int)((__libc_ctype_ + 1)[(c)] & _C)) -#define tolower(c) ((int)((__libc_tolower_tab_ + 1)[(c)])) -#define toupper(c) ((int)((__libc_toupper_tab_ + 1)[(c)])) +#define _CTYPE_NUM_CHARS (1 << (8*sizeof(char))) + +static __inline int +__libc_ctype_index(__uint16_t mask, int c) +{ + if (c < -1 || c >= _CTYPE_NUM_CHARS) + return(0); /* XXX maybe assert instead? */ + return(__libc_ctype_[c + 1] & mask); +} + +static __inline int +__libc_ctype_convert(__int16_t *array, int c) +{ + if (c < -1 || c >= _CTYPE_NUM_CHARS) + return(c); /* XXX maybe assert instead? */ + return(array[c + 1]); +} + +#ifndef _CTYPE_PRIVATE +#undef _CTYPE_NUM_CHARS +#endif + +#define isdigit(c) __libc_ctype_index(_D, c) +#define islower(c) __libc_ctype_index(_L, c) +#define isspace(c) __libc_ctype_index(_S, c) +#define ispunct(c) __libc_ctype_index(_P, c) +#define isupper(c) __libc_ctype_index(_U, c) +#define isalpha(c) __libc_ctype_index(_A, c) +#define isxdigit(c) __libc_ctype_index(_X, c) +#define isalnum(c) __libc_ctype_index(_A|_D, c) +#define isprint(c) __libc_ctype_index(_R, c) +#define isgraph(c) __libc_ctype_index(_G, c) +#define iscntrl(c) __libc_ctype_index(_C, c) +#define tolower(c) __libc_ctype_convert(__libc_tolower_tab_, c) +#define toupper(c) __libc_ctype_convert(__libc_toupper_tab_, c) #if defined(__XSI_VISIBLE) #define isascii(c) ((unsigned)(c) <= 0177) @@ -111,17 +143,7 @@ __END_DECLS #if __ISO_C_VISIBLE >= 1999 || __POSIX_VISIBLE >= 200112L || \ __XSI_VISIBLE >= 600 -#define isblank(c) ((int)((__libc_ctype_ + 1)[(c)] & _B)) -#endif - -#ifdef _CTYPE_PRIVATE -#include /* for CHAR_BIT */ - -#define _CTYPE_NUM_CHARS (1 << CHAR_BIT) - -extern const __uint16_t __libc_C_ctype_[]; -extern const __int16_t __libc_C_toupper_[]; -extern const __int16_t __libc_C_tolower_[]; +#define isblank(c) __libc_ctype_index(_B, c) #endif #endif /* !_CTYPE_H_DISABLE_MACROS_ */ diff --git a/lib/libc/gen/isctype.c b/lib/libc/gen/isctype.c index d1ded39a8f..640d272b9a 100644 --- a/lib/libc/gen/isctype.c +++ b/lib/libc/gen/isctype.c @@ -1,5 +1,5 @@ /* $NetBSD: src/lib/libc/gen/isctype.c,v 1.16 2003/08/07 16:42:52 agc Exp $ */ -/* $DragonFly: src/lib/libc/gen/isctype.c,v 1.4 2005/05/08 15:52:05 joerg Exp $ */ +/* $DragonFly: src/lib/libc/gen/isctype.c,v 1.5 2005/07/07 07:17:47 dillon Exp $ */ /* * Copyright (c) 1989 The Regents of the University of California. @@ -42,84 +42,84 @@ int isalnum(int c) { - return((__libc_ctype_ + 1)[c] & (_A|_D)); + return(__libc_ctype_index(_A|_D, c)); } #undef isalpha int isalpha(int c) { - return((__libc_ctype_ + 1)[c] & (_A)); + return(__libc_ctype_index(_A, c)); } #undef isblank int isblank(int c) { - return((__libc_ctype_ + 1)[c] & _B); + return(__libc_ctype_index(_B, c)); } #undef iscntrl int iscntrl(int c) { - return((__libc_ctype_ + 1)[c] & _C); + return(__libc_ctype_index(_C, c)); } #undef isdigit int isdigit(int c) { - return((__libc_ctype_ + 1)[c] & _D); + return(__libc_ctype_index(_D, c)); } #undef isgraph int isgraph(int c) { - return((__libc_ctype_ + 1)[c] & (_G)); + return(__libc_ctype_index(_G, c)); } #undef islower int islower(int c) { - return((__libc_ctype_ + 1)[c] & _L); + return(__libc_ctype_index(_L, c)); } #undef isprint int isprint(int c) { - return((__libc_ctype_ + 1)[c] & (_R)); + return(__libc_ctype_index(_R, c)); } #undef ispunct int ispunct(int c) { - return((__libc_ctype_ + 1)[c] & _P); + return(__libc_ctype_index(_P, c)); } #undef isspace int isspace(int c) { - return((__libc_ctype_ + 1)[c] & _S); + return(__libc_ctype_index(_S, c)); } #undef isupper int isupper(int c) { - return((__libc_ctype_ + 1)[c] & _U); + return(__libc_ctype_index(_U, c)); } #undef isxdigit int isxdigit(int c) { - return((__libc_ctype_ + 1)[c] & (_X)); + return(__libc_ctype_index(_X, c)); } #undef _toupper diff --git a/lib/libc/gen/tolower.c b/lib/libc/gen/tolower.c index c70773c7ea..e266132ead 100644 --- a/lib/libc/gen/tolower.c +++ b/lib/libc/gen/tolower.c @@ -1,5 +1,5 @@ /* $NetBSD: src/lib/libc/gen/tolower_.c,v 1.9 2003/07/26 19:24:45 salo Exp $ */ -/* $DragonFly: src/lib/libc/gen/tolower.c,v 1.1 2005/04/21 16:36:34 joerg Exp $ */ +/* $DragonFly: src/lib/libc/gen/tolower.c,v 1.2 2005/07/07 07:17:47 dillon Exp $ */ /* * Written by J.T. Conklin . @@ -56,5 +56,5 @@ const int16_t *__libc_tolower_tab_ = __libc_C_tolower_; int tolower(int c) { - return((__libc_tolower_tab_ + 1)[c]); + return(__libc_ctype_convert(__libc_tolower_tab_, c)); } diff --git a/lib/libc/gen/toupper.c b/lib/libc/gen/toupper.c index df2423a82d..7a095fd9e7 100644 --- a/lib/libc/gen/toupper.c +++ b/lib/libc/gen/toupper.c @@ -1,5 +1,5 @@ /* $NetBSD: src/lib/libc/gen/toupper_.c,v 1.9 2003/07/26 19:24:45 salo Exp $ */ -/* $DragonFly: src/lib/libc/gen/toupper.c,v 1.1 2005/04/21 16:36:34 joerg Exp $ */ +/* $DragonFly: src/lib/libc/gen/toupper.c,v 1.2 2005/07/07 07:17:47 dillon Exp $ */ /* * Written by J.T. Conklin . @@ -56,5 +56,5 @@ const int16_t *__libc_toupper_tab_ = __libc_C_toupper_; int toupper(int c) { - return((__libc_toupper_tab_ + 1)[c]); + return(__libc_ctype_convert(__libc_toupper_tab_, c)); } -- 2.41.0