/[pcre]/code/branches/pcre16/pcre_byte_order.c
ViewVC logotype

Diff of /code/branches/pcre16/pcre_byte_order.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

code/branches/pcre16/pcre_try_flipped.c revision 774 by zherczeg, Thu Dec 1 06:08:45 2011 UTC code/branches/pcre16/pcre_byte_order.c revision 809 by zherczeg, Mon Dec 19 11:04:45 2011 UTC
# Line 51  auxiliary local function to flip the app Line 51  auxiliary local function to flip the app
51    
52    
53  /*************************************************  /*************************************************
54  *         Flip bytes in an integer               *  *             Swap byte functions                *
55  *************************************************/  *************************************************/
56    
57  /* This function is called when the magic number in a regex doesn't match, in  /* The following functions swap the bytes of a pcre_uint16
58  order to flip its bytes to see if we are dealing with a pattern that was  and pcre_uint32 value.
 compiled on a host of different endianness. If so, this function is used to  
 flip other byte values.  
59    
60  Arguments:  Arguments:
61    value        the number to flip    value        any number
   n            the number of bytes to flip (assumed to be 2 or 4)  
62    
63  Returns:       the flipped value  Returns:       the byte swapped value
64  */  */
65    
66  static unsigned long int  static pcre_uint32
67  byteflip(unsigned long int value, int n)  swap_uint32(pcre_uint32 value)
68  {  {
 if (n == 2) return ((value & 0x00ff) << 8) | ((value & 0xff00) >> 8);  
69  return ((value & 0x000000ff) << 24) |  return ((value & 0x000000ff) << 24) |
70         ((value & 0x0000ff00) <<  8) |         ((value & 0x0000ff00) <<  8) |
71         ((value & 0x00ff0000) >>  8) |         ((value & 0x00ff0000) >>  8) |
72         ((value & 0xff000000) >> 24);         (value >> 24);
73  }  }
74    
75    static pcre_uint16
76    swap_uint16(pcre_uint16 value)
77    {
78    return (value >> 8) | (value << 8);
79    }
80    
81    
82  /*************************************************  /*************************************************
83  *       Test for a byte-flipped compiled regex   *  *       Test for a byte-flipped compiled regex   *
84  *************************************************/  *************************************************/
85    
86  /* This function is called from pcre_exec(), pcre_dfa_exec(), and also from  /* This function swaps the bytes of a compiled pattern usually
87  pcre_fullinfo(). Its job is to test whether the regex is byte-flipped - that  loaeded form the disk. It also sets the tables pointer, which
88  is, it was compiled on a system of opposite endianness. The function is called  is likely an invalid pointer after reload.
 only when the native MAGIC_NUMBER test fails. If the regex is indeed flipped,  
 we flip all the relevant values into a different data block, and return it.  
89    
90  Arguments:  Arguments:
91    re               points to the regex    argument_re     points to the compiled expression
92    study            points to study data, or NULL    extra_data      points to extra data or is NULL
93    internal_re      points to a new regex block    tables          points to the character tables or NULL
   internal_study   points to a new study block  
94    
95  Returns:           the new block if is is indeed a byte-flipped regex  Returns:          0 if the swap is successful, negative on error
                    NULL if it is not  
96  */  */
97    
98  real_pcre *  #ifdef COMPILE_PCRE8
99  PRIV(try_flipped)(const real_pcre *re, real_pcre *internal_re,  PCRE_EXP_DECL int pcre_pattern_to_host_byte_order(pcre *argument_re,
100    const pcre_study_data *study, pcre_study_data *internal_study)    pcre_extra *extra_data, const unsigned char *tables)
101    #else
102    PCRE_EXP_DECL int pcre16_pattern_to_host_byte_order(pcre *argument_re,
103      pcre_extra *extra_data, const unsigned char *tables)
104    #endif
105  {  {
106  if (byteflip(re->magic_number, sizeof(re->magic_number)) != MAGIC_NUMBER)  real_pcre *re = (real_pcre *)argument_re;
107    return NULL;  pcre_study_data *study;
108    #ifndef COMPILE_PCRE8
109    pcre_uchar *ptr;
110    int length;
111    #ifdef SUPPORT_UTF
112    BOOL utf;
113    BOOL utf16_char;
114    #endif /* SUPPORT_UTF */
115    #endif /* !COMPILE_PCRE8 */
116    
117    if (re == NULL) return PCRE_ERROR_NULL;
118    if (re->magic_number == MAGIC_NUMBER)
119      {
120      if ((re->flags & PCRE_MODE) == 0) return PCRE_ERROR_BADMODE;
121      re->tables = tables;
122      return 0;
123      }
124    
125    if (re->magic_number != REVERSED_MAGIC_NUMBER) return PCRE_ERROR_BADMAGIC;
126    if ((swap_uint16(re->flags)  & PCRE_MODE) == 0) return PCRE_ERROR_BADMODE;
127    
128    re->magic_number = MAGIC_NUMBER;
129    re->size = swap_uint32(re->size);
130    re->options = swap_uint32(re->options);
131    re->flags = swap_uint16(re->flags);
132    re->top_bracket = swap_uint16(re->top_bracket);
133    re->top_backref = swap_uint16(re->top_backref);
134    re->first_char = swap_uint16(re->first_char);
135    re->req_char = swap_uint16(re->req_char);
136    re->name_table_offset = swap_uint16(re->name_table_offset);
137    re->name_entry_size = swap_uint16(re->name_entry_size);
138    re->name_count = swap_uint16(re->name_count);
139    re->ref_count = swap_uint16(re->ref_count);
140    
141    if (extra_data != NULL && (re->flags & PCRE_EXTRA_STUDY_DATA) != 0)
142      {
143      study = (pcre_study_data *)extra_data->study_data;
144      study->size = swap_uint32(study->size);
145      study->flags = swap_uint32(study->flags);
146      study->minlength = swap_uint32(study->minlength);
147      }
148    
149  *internal_re = *re;           /* To copy other fields */  #ifndef COMPILE_PCRE8
150  internal_re->size = byteflip(re->size, sizeof(re->size));  ptr = (pcre_uchar *)re + re->name_table_offset;
151  internal_re->options = byteflip(re->options, sizeof(re->options));  length = re->name_count * re->name_entry_size;
152  internal_re->flags = (pcre_uint16)byteflip(re->flags, sizeof(re->flags));  #ifdef SUPPORT_UTF
153  internal_re->top_bracket =  utf = (re->options & PCRE_UTF16) != 0;
154    (pcre_uint16)byteflip(re->top_bracket, sizeof(re->top_bracket));  utf16_char = FALSE;
155  internal_re->top_backref =  #endif
   (pcre_uint16)byteflip(re->top_backref, sizeof(re->top_backref));  
 internal_re->first_char =  
   (pcre_uint16)byteflip(re->first_char, sizeof(re->first_char));  
 internal_re->req_char =  
   (pcre_uint16)byteflip(re->req_char, sizeof(re->req_char));  
 internal_re->name_table_offset =  
   (pcre_uint16)byteflip(re->name_table_offset, sizeof(re->name_table_offset));  
 internal_re->name_entry_size =  
   (pcre_uint16)byteflip(re->name_entry_size, sizeof(re->name_entry_size));  
 internal_re->name_count =  
   (pcre_uint16)byteflip(re->name_count, sizeof(re->name_count));  
156    
157  if (study != NULL)  while(TRUE)
158    {    {
159    *internal_study = *study;   /* To copy other fields */    /* Swap previous characters. */
160    internal_study->size = byteflip(study->size, sizeof(study->size));    while (length-- > 0)
161    internal_study->flags = byteflip(study->flags, sizeof(study->flags));      {
162    internal_study->minlength = byteflip(study->minlength,      *ptr = swap_uint16(*ptr);
163      sizeof(study->minlength));      ptr++;
164        }
165    #ifdef SUPPORT_UTF
166      if (utf16_char)
167        {
168        if (HAS_EXTRALEN(ptr[-1]))
169          {
170          /* We know that there is only one extra character in UTF-16. */
171          *ptr = swap_uint16(*ptr);
172          ptr++;
173          }
174        }
175      utf16_char = FALSE;
176    #endif /* SUPPORT_UTF */
177    
178      /* Get next opcode. */
179      length = 0;
180      *ptr = swap_uint16(*ptr);
181      switch (*ptr)
182        {
183        case OP_END:
184        return 0;
185    
186        case OP_CHAR:
187        case OP_CHARI:
188        case OP_NOT:
189        case OP_NOTI:
190        case OP_STAR:
191        case OP_MINSTAR:
192        case OP_PLUS:
193        case OP_MINPLUS:
194        case OP_QUERY:
195        case OP_MINQUERY:
196        case OP_UPTO:
197        case OP_MINUPTO:
198        case OP_EXACT:
199        case OP_POSSTAR:
200        case OP_POSPLUS:
201        case OP_POSQUERY:
202        case OP_POSUPTO:
203        case OP_STARI:
204        case OP_MINSTARI:
205        case OP_PLUSI:
206        case OP_MINPLUSI:
207        case OP_QUERYI:
208        case OP_MINQUERYI:
209        case OP_UPTOI:
210        case OP_MINUPTOI:
211        case OP_EXACTI:
212        case OP_POSSTARI:
213        case OP_POSPLUSI:
214        case OP_POSQUERYI:
215        case OP_POSUPTOI:
216        case OP_NOTSTAR:
217        case OP_NOTMINSTAR:
218        case OP_NOTPLUS:
219        case OP_NOTMINPLUS:
220        case OP_NOTQUERY:
221        case OP_NOTMINQUERY:
222        case OP_NOTUPTO:
223        case OP_NOTMINUPTO:
224        case OP_NOTEXACT:
225        case OP_NOTPOSSTAR:
226        case OP_NOTPOSPLUS:
227        case OP_NOTPOSQUERY:
228        case OP_NOTPOSUPTO:
229        case OP_NOTSTARI:
230        case OP_NOTMINSTARI:
231        case OP_NOTPLUSI:
232        case OP_NOTMINPLUSI:
233        case OP_NOTQUERYI:
234        case OP_NOTMINQUERYI:
235        case OP_NOTUPTOI:
236        case OP_NOTMINUPTOI:
237        case OP_NOTEXACTI:
238        case OP_NOTPOSSTARI:
239        case OP_NOTPOSPLUSI:
240        case OP_NOTPOSQUERYI:
241        case OP_NOTPOSUPTOI:
242        utf16_char = TRUE;
243        length = PRIV(OP_lengths)[*ptr] - 1;
244        break;
245    
246        case OP_CLASS:
247        case OP_NCLASS:
248        /* Skip the character bit map. */
249        ptr += 32/sizeof(pcre_uchar);
250        length = 0;
251        break;
252    
253        case OP_XCLASS:
254        /* Reverse the size of the XCLASS instance. */
255        ptr++;
256        *ptr = swap_uint16(*ptr);
257        if (LINK_SIZE > 1)
258          {
259          /* LINK_SIZE can be 1 or 2 in 16 bit mode. */
260          ptr++;
261          *ptr = swap_uint16(*ptr);
262          }
263        ptr++;
264        length = (GET(ptr, -LINK_SIZE)) - (1 + LINK_SIZE + 1);
265        *ptr = swap_uint16(*ptr);
266        if ((*ptr & XCL_MAP) != 0)
267          {
268          /* Skip the character bit map. */
269          ptr += 32/sizeof(pcre_uchar);
270          length -= 32/sizeof(pcre_uchar);
271          }
272        break;
273    
274        default:
275        length = PRIV(OP_lengths)[*ptr] - 1;
276        break;
277        }
278      ptr++;
279    }    }
280    /* Control should never reach here in 16 bit mode. */
281    #endif /* !COMPILE_PCRE8 */
282    
283  return internal_re;  return 0;
284  }  }
285    
286  /* End of pcre_tryflipped.c */  /* End of pcre_byte_order.c */

Legend:
Removed from v.774  
changed lines
  Added in v.809

webmaster@exim.org
ViewVC Help
Powered by ViewVC 1.1.12