This is the mail archive of the libc-alpha@sourceware.org mailing list for the glibc project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [PATCH][RFC] Avoid table lookup in isascii, isxdigit.


On Tue, Apr 09, 2013 at 09:28:11AM -0400, Carlos O'Donell wrote:
> On 04/09/2013 07:57 AM, OndÅej BÃlka wrote:
> > Hi, I looked to ctype and thougth if it is possible to decrease table
> > size to 512 bytes. I did not succeed but made following three
> > optimizations.
> > 
> > 1. In isdigit use & instead &&. Gcc contains bug that optimizes first
> > but not second case.
> > 2. Refactor isdigit macro
> > 3. Write isxdigit and isascii.
> 
> You should add a microbenchmark for isdigit, isascii, and isxdigit :-)
>  
I need to do hooking as I did before. This is memory access vs no memory
access situation I do not cache miss rate. 

When both access memory with same pattern then microbenchmark suffices
because both are slowed by same (but unknown) amount.

> > Following code is enclosed in
> > 
> > #ifndef _ISOMAC
> > # if !defined __NO_CTYPE && !defined NOT_IN_libc
> 
> If we are not testing for ISO C compliance, and
> we are not building ctype.c or ctype_l.c, and we
> are building libc...
> 
> > Is there reason why we cannot also transform user code in this way?
> 
> User code must consult LC_CTYPE to get this correct?
>
Not sure about this

I found in ISO/IEC 9899:TC3 :

7.4.1.12 The isxdigit function
Synopsis
1 #include <ctype.h>
int isxdigit(int c);
Description
2 The isxdigit function tests for any hexadecimal-digit character (as
defined in 6.4.4.1). 

Probably I could optimize is* more if I had quaranteee that single byte 
locales are ascii compatible. Then we can handle common ascii case
without memory access and call function only when c>=128.


> > ---
> >  include/ctype.h |   23 ++++++++++++++++++++---
> >  1 files changed, 20 insertions(+), 3 deletions(-)
> > 
> > diff --git a/include/ctype.h b/include/ctype.h
> > index 6a18039..7f9e928 100644
> > --- a/include/ctype.h
> > +++ b/include/ctype.h
> > @@ -56,11 +56,28 @@ __ctype_tolower_loc (void)
> >  /* The spec says that isdigit must only match the decimal digits.  We
> >     can check this without a memory access.  */
> >  #  undef isdigit
> > -#  define isdigit(c) ({ int __c = (c); __c >= '0' && __c <= '9'; })
> > +#  define isdigit(c) ({ int __c = (c); (__c >= '0') & (__c <= '9'); })
> >  #  undef isdigit_l
> > -#  define isdigit_l(c, l) ({ int __c = (c); __c >= '0' && __c <= '9'; })
> > +#  define isdigit_l(c, l) isdigit(c)
> >  #  undef __isdigit_l
> > -#  define __isdigit_l(c, l) ({ int __c = (c); __c >= '0' && __c <= '9'; })
> > +#  define __isdigit_l(c, l) isdigit(c)
> > +
> > +/* The spec says that isxdigit must only match the hexadecimal digits.  We
> > +   can check this without a memory access.  */
> > +#  undef isxdigit
> > +#  define isxdigit(c) ({ int __c = (c); ((__c >= '0') & (__c <= '9')) || ((__c >= 'a') & (__c <= 'f')) || ((__c >= 'A') & (__c <= 'F')); })
> > +#  undef isxdigit_l
> > +#  define isxdigit_l(c, l) isxdigit(c)
> > +#  undef __isxdigit_l
> > +#  define __isxdigit_l(c, l) isxdigit(c)
> > +
> > +#  undef isascii
> > +#  define isascii(c) ({ int __c = (c); (__c & 128 == 0); })
> > +#  undef isascii_l
> > +#  define isascii_l(c, l) isascii(c)
> > +#  undef __isascii_l
> > +#  define __isascii_l(c, l) isascii(c)
> > +
> >  # endif
> >  #endif
> >  
> > 
> 
> Cheers,
> Carlos.
> 



Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]