OSDN Git Service

e8324caf4e4d218627d900c25a9375783b2c4043
[pf3gnuchains/gcc-fork.git] / gcc / c-pragma.c
1 /* Handle #pragma, system V.4 style.  Supports #pragma weak and #pragma pack.
2    Copyright (C) 1992 Free Software Foundation, Inc.
3
4 This file is part of GNU CC.
5
6 GNU CC is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2, or (at your option)
9 any later version.
10
11 GNU CC is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with GNU CC; see the file COPYING.  If not, write to
18 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */
19
20 #include <stdio.h>
21 #include "config.h"
22 #include "tree.h"
23
24 #ifdef HANDLE_SYSV_PRAGMA
25
26 /* When structure field packing is in effect, this variable is the
27    number of bits to use as the maximum alignment.  When packing is not
28    in effect, this is zero. */
29
30 extern int maximum_field_alignment;
31
32 /* Handle one token of a pragma directive.  TOKEN is the
33    current token, and STRING is its printable form.  */
34
35 void
36 handle_pragma_token (string, token)
37      char *string;
38      tree token;
39 {
40   static enum pragma_state
41     {
42       ps_start,
43       ps_done,
44       ps_bad,
45       ps_weak,
46       ps_name,
47       ps_equals,
48       ps_value,
49       ps_pack,
50       ps_left,
51       ps_align,
52       ps_right
53       } state = ps_start, type;
54   static char *name;
55   static char *value;
56   static int align;
57
58   if (string == 0)
59     {
60       if (type == ps_pack)
61         {
62           if (state == ps_right)
63             maximum_field_alignment = align * 8;
64           else
65             warning ("malformed `#pragma pack'");
66         }
67 #ifdef WEAK_ASM_OP
68       else if (type == ps_weak)
69         {
70           if (state == ps_name || state == ps_value)
71             {
72               fprintf (asm_out_file, "\t%s\t", WEAK_ASM_OP);
73               ASM_OUTPUT_LABELREF (asm_out_file, name);
74               fputc ('\n', asm_out_file);
75               if (state == ps_value)
76                 {
77                   fprintf (asm_out_file, "\t%s\t", SET_ASM_OP);
78                   ASM_OUTPUT_LABELREF (asm_out_file, name);
79                   fputc (',', asm_out_file);
80                   ASM_OUTPUT_LABELREF (asm_out_file, value);
81                   fputc ('\n', asm_out_file);
82                 }
83             }
84           else if (! (state == ps_done || state == ps_start))
85             warning ("malformed `#pragma weak'");
86         }
87 #endif /* WEAK_ASM_OP */
88
89       type = state = ps_start;
90       return;
91     }
92
93   switch (state)
94     {
95     case ps_start:
96       if (token && TREE_CODE (token) == IDENTIFIER_NODE)
97         {
98           if (strcmp (IDENTIFIER_POINTER (token), "pack") == 0)
99             type = state = ps_pack;
100 #ifdef WEAK_ASM_OP
101           else if (strcmp (IDENTIFIER_POINTER (token), "weak") == 0)
102             type = state = ps_weak;
103 #endif
104           else
105             type = state = ps_done;
106         }
107       else
108         type = state = ps_done;
109       break;
110
111 #ifdef WEAK_ASM_OP
112     case ps_weak:
113       if (token && TREE_CODE (token) == IDENTIFIER_NODE)
114         {
115           name = IDENTIFIER_POINTER (token);
116           state = ps_name;
117         }
118       else
119         state = ps_bad;
120       break;
121
122     case ps_name:
123       state = (strcmp (string, "=") ? ps_bad : ps_equals);
124       break;
125
126     case ps_equals:
127       if (token && TREE_CODE (token) == IDENTIFIER_NODE)
128         {
129           value = IDENTIFIER_POINTER (token);
130           state = ps_value;
131         }
132       else
133         state = ps_bad;
134       break;
135
136     case ps_value:
137       state = ps_bad;
138       break;
139 #endif /* WEAK_ASM_OP */
140
141     case ps_pack:
142       if (strcmp (string, "(") == 0)
143         state = ps_left;
144       else
145         state = ps_bad;
146       break;
147
148     case ps_left:
149       if (token && TREE_CODE (token) == INTEGER_CST
150           && TREE_INT_CST_HIGH (token) == 0)
151         switch (TREE_INT_CST_LOW (token))
152           {
153           case 1:
154           case 2:
155           case 4:
156             align = TREE_INT_CST_LOW (token);
157             state = ps_align;
158             break;
159
160           default:
161             state = ps_bad;
162           }
163       else if (! token && strcmp (string, ")") == 0)
164         {
165           align = 0;
166           state = ps_right;
167         }
168       else
169         state = ps_bad;
170       break;
171
172     case ps_align:
173       if (strcmp (string, ")") == 0)
174         state = ps_right;
175       else
176         state = ps_bad;
177       break;
178
179     case ps_right:
180       state = ps_bad;
181       break;
182
183     case ps_bad:
184     case ps_done:
185       break;
186
187     default:
188       abort ();
189     }
190 }
191 #endif /* HANDLE_SYSV_PRAGMA */