Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 /* | 1 /* |
| 2 * Copyright (c) 2012 The Native Client Authors. All rights reserved. | 2 * Copyright (c) 2012 The Native Client Authors. All rights reserved. |
| 3 * Use of this source code is governed by a BSD-style license that can be | 3 * Use of this source code is governed by a BSD-style license that can be |
| 4 * found in the LICENSE file. | 4 * found in the LICENSE file. |
| 5 */ | 5 */ |
| 6 | 6 |
| 7 #include <assert.h> | 7 #include <assert.h> |
| 8 #include <stddef.h> | 8 #include <stddef.h> |
| 9 #include <stdio.h> | 9 #include <stdio.h> |
| 10 #include <stdlib.h> | 10 #include <stdlib.h> |
| (...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 81 action rel16_operand { | 81 action rel16_operand { |
| 82 assert(FALSE); | 82 assert(FALSE); |
| 83 } | 83 } |
| 84 action rel32_operand { | 84 action rel32_operand { |
| 85 int32_t offset = | 85 int32_t offset = |
| 86 (uint32_t) (p[-3] + 256U * (p[-2] + 256U * (p[-1] + 256U * (p[0])))); | 86 (uint32_t) (p[-3] + 256U * (p[-2] + 256U * (p[-1] + 256U * (p[0])))); |
| 87 size_t jump_dest = offset + (p - data); | 87 size_t jump_dest = offset + (p - data); |
| 88 check_jump_dest; | 88 check_jump_dest; |
| 89 } | 89 } |
| 90 | 90 |
| 91 include decode_x86_64 "validator-x86_64-instruction.rl"; | 91 action process_0_operands { |
| 92 | |
| 93 action process_normal_instruction { | |
| 94 /* Restricted %rsp or %rbp must be processed by appropriate nacl-special | 92 /* Restricted %rsp or %rbp must be processed by appropriate nacl-special |
| 95 instruction, not with regular instruction. */ | 93 instruction, not with regular instruction. */ |
| 96 if (restricted_register == REG_RSP) { | 94 if (restricted_register == REG_RSP) { |
| 95 PrintError("Incorrectly modified register %%rsp\n", begin - data); | |
| 96 result = 1; | |
| 97 goto error_detected; | |
| 98 } else if (restricted_register == REG_RBP) { | |
| 99 PrintError("Incorrectly modified register %%rbp\n", begin - data); | |
| 100 result = 1; | |
| 101 goto error_detected; | |
| 102 } | |
| 103 restricted_register = kNoRestrictedReg; | |
| 104 } | |
| 105 | |
| 106 action process_1_operands { | |
| 107 /* Restricted %rsp or %rbp must be processed by appropriate nacl-special | |
| 108 instruction, not with regular instruction. */ | |
| 109 if (restricted_register == REG_RSP) { | |
| 97 PrintError("Incorrectly modified register %%rsp\n", begin - data); | 110 PrintError("Incorrectly modified register %%rsp\n", begin - data); |
| 98 result = 1; | 111 result = 1; |
| 99 goto error_detected; | 112 goto error_detected; |
| 100 } else if (restricted_register == REG_RBP) { | 113 } else if (restricted_register == REG_RBP) { |
| 101 PrintError("Incorrectly modified register %%rbp\n", begin - data); | 114 PrintError("Incorrectly modified register %%rbp\n", begin - data); |
| 102 result = 1; | 115 result = 1; |
| 103 goto error_detected; | 116 goto error_detected; |
| 104 } | 117 } |
| 105 /* If Sandboxed Rsi is destroyed then we must note that. */ | 118 /* If Sandboxed Rsi is destroyed then we must note that. */ |
|
pasko-google - do not use
2012/05/12 13:54:31
s/note/detect/
khim
2012/05/12 14:32:16
Done.
| |
| 106 if (restricted_register == kSandboxedRsi) { | 119 if (restricted_register == kSandboxedRsi) { |
| 107 if (CHECK_OPERAND(0, REG_RSI, OperandSandboxRestricted) || | 120 if (CHECK_OPERAND(0, REG_RSI, OperandSandboxRestricted) || |
| 121 CHECK_OPERAND(0, REG_RSI, OperandSandboxUnrestricted)) { | |
| 122 restricted_register = kNoRestrictedReg; | |
| 123 } | |
| 124 } | |
| 125 if (restricted_register == kSandboxedRsi) { | |
| 126 if (CHECK_OPERAND(0, REG_RDI, OperandSandboxRestricted)) { | |
| 127 sandboxed_rsi_restricted_rdi = begin; | |
| 128 restricted_register = kSandboxedRsiRestrictedRdi; | |
| 129 } | |
| 130 } | |
| 131 if (restricted_register != kSandboxedRsiRestrictedRdi) { | |
| 132 restricted_register = kNoRestrictedReg; | |
| 133 if (CHECK_OPERAND(0, REG_R15, OperandSandbox8bit) || | |
| 134 CHECK_OPERAND(0, REG_R15, OperandSandboxRestricted) || | |
| 135 CHECK_OPERAND(0, REG_R15, OperandSandboxUnrestricted)) { | |
| 136 PrintError("Incorrectly modified register %%r15\n", begin - data); | |
| 137 result = 1; | |
| 138 goto error_detected; | |
| 139 } else if ((CHECK_OPERAND(0, REG_RBP, OperandSandbox8bit) && | |
| 140 GET_REX_PREFIX()) || | |
| 141 CHECK_OPERAND(0, REG_RBP, OperandSandboxUnrestricted)) { | |
| 142 PrintError("Incorrectly modified register %%rbp\n", begin - data); | |
| 143 result = 1; | |
| 144 goto error_detected; | |
| 145 } else if ((CHECK_OPERAND(0, REG_RSP, OperandSandbox8bit) && | |
| 146 GET_REX_PREFIX()) || | |
| 147 CHECK_OPERAND(0, REG_RSP, OperandSandboxUnrestricted)) { | |
| 148 PrintError("Incorrectly modified register %%rsp\n", begin - data); | |
| 149 result = 1; | |
| 150 goto error_detected; | |
| 151 } else if ((operand_states & 0x70) == (OperandSandboxRestricted << 5)) { | |
| 152 restricted_register = operand_states & 0x0f; | |
|
pasko-google - do not use
2012/05/12 13:54:31
copy the proposed comment above this line too
khim
2012/05/12 14:32:16
Done.
| |
| 153 } | |
| 154 } | |
| 155 } | |
| 156 | |
| 157 action process_2_operands { | |
| 158 /* Restricted %rsp or %rbp must be processed by appropriate nacl-special | |
| 159 instruction, not with regular instruction. */ | |
| 160 if (restricted_register == REG_RSP) { | |
| 161 PrintError("Incorrectly modified register %%rsp\n", begin - data); | |
| 162 result = 1; | |
| 163 goto error_detected; | |
| 164 } else if (restricted_register == REG_RBP) { | |
| 165 PrintError("Incorrectly modified register %%rbp\n", begin - data); | |
| 166 result = 1; | |
| 167 goto error_detected; | |
| 168 } | |
| 169 /* If Sandboxed Rsi is destroyed then we must note that. */ | |
|
pasko-google - do not use
2012/05/12 13:54:31
ditto
khim
2012/05/12 14:32:16
Done.
| |
| 170 if (restricted_register == kSandboxedRsi) { | |
| 171 if (CHECK_OPERAND(0, REG_RSI, OperandSandboxRestricted) || | |
| 108 CHECK_OPERAND(0, REG_RSI, OperandSandboxUnrestricted) || | 172 CHECK_OPERAND(0, REG_RSI, OperandSandboxUnrestricted) || |
| 109 CHECK_OPERAND(1, REG_RSI, OperandSandboxRestricted) || | 173 CHECK_OPERAND(1, REG_RSI, OperandSandboxRestricted) || |
| 110 CHECK_OPERAND(1, REG_RSI, OperandSandboxUnrestricted)) { | 174 CHECK_OPERAND(1, REG_RSI, OperandSandboxUnrestricted)) { |
| 111 restricted_register = kNoRestrictedReg; | 175 restricted_register = kNoRestrictedReg; |
| 112 } | 176 } |
| 113 } | 177 } |
| 114 if (restricted_register == kSandboxedRsi) { | 178 if (restricted_register == kSandboxedRsi) { |
| 115 if (CHECK_OPERAND(0, REG_RDI, OperandSandboxRestricted) || | 179 if (CHECK_OPERAND(0, REG_RDI, OperandSandboxRestricted) || |
| 116 CHECK_OPERAND(1, REG_RDI, OperandSandboxRestricted)) { | 180 CHECK_OPERAND(1, REG_RDI, OperandSandboxRestricted)) { |
| 117 sandboxed_rsi_restricted_rdi = begin; | 181 sandboxed_rsi_restricted_rdi = begin; |
| (...skipping 23 matching lines...) Expand all Loading... | |
| 141 } else if ((CHECK_OPERAND(0, REG_RSP, OperandSandbox8bit) && | 205 } else if ((CHECK_OPERAND(0, REG_RSP, OperandSandbox8bit) && |
| 142 GET_REX_PREFIX()) || | 206 GET_REX_PREFIX()) || |
| 143 CHECK_OPERAND(0, REG_RSP, OperandSandboxUnrestricted) || | 207 CHECK_OPERAND(0, REG_RSP, OperandSandboxUnrestricted) || |
| 144 (CHECK_OPERAND(1, REG_RSP, OperandSandbox8bit) && | 208 (CHECK_OPERAND(1, REG_RSP, OperandSandbox8bit) && |
| 145 GET_REX_PREFIX()) || | 209 GET_REX_PREFIX()) || |
| 146 CHECK_OPERAND(1, REG_RSP, OperandSandboxUnrestricted)) { | 210 CHECK_OPERAND(1, REG_RSP, OperandSandboxUnrestricted)) { |
| 147 PrintError("Incorrectly modified register %%rsp\n", begin - data); | 211 PrintError("Incorrectly modified register %%rsp\n", begin - data); |
| 148 result = 1; | 212 result = 1; |
| 149 goto error_detected; | 213 goto error_detected; |
| 150 } else if ((operand_states & 0x70) == (OperandSandboxRestricted << 5)) { | 214 } else if ((operand_states & 0x70) == (OperandSandboxRestricted << 5)) { |
| 151 restricted_register = operand_states & 0x0f; | 215 restricted_register = operand_states & 0x0f; |
|
pasko-google - do not use
2012/05/12 13:54:31
/* Take 2 bits of operand type from "operand_state
khim
2012/05/12 14:32:16
Done.
| |
| 152 } else if ((operand_states & 0x7000) == | 216 } else if ((operand_states & 0x7000) == |
| 153 (OperandSandboxRestricted << (5 + 8))) { | 217 (OperandSandboxRestricted << (5 + 8))) { |
|
pasko-google - do not use
2012/05/12 13:54:31
align with shiftwidth=4
khim
2012/05/12 14:32:16
Done.
| |
| 154 restricted_register = (operand_states & 0x0f00) >> 8; | 218 restricted_register = (operand_states & 0x0f00) >> 8; |
| 155 } | 219 } |
| 156 } | 220 } |
| 157 } | 221 } |
| 158 | 222 |
| 223 include decode_x86_64 "validator-x86_64-instruction.rl"; | |
| 224 | |
| 159 # Remove special instructions which are only allowed in special cases. | 225 # Remove special instructions which are only allowed in special cases. |
| 160 normal_instruction = (one_instruction - ( | 226 normal_instruction = one_instruction - ( |
| 161 (0x48 0x89 0xe5) | # mov %rsp,%rbp | 227 (0x48 0x89 0xe5) | # mov %rsp,%rbp |
| 162 (0x48 0x89 0xec) | # mov %rbp,%rsp | 228 (0x48 0x89 0xec) | # mov %rbp,%rsp |
| 163 (0x48 0x81 0xe4 any{4}) | # and $XXX,%rsp | 229 (0x48 0x81 0xe4 any{4}) | # and $XXX,%rsp |
| 164 (0x48 0x83 0xe4 any) | # and $XXX,%rsp | 230 (0x48 0x83 0xe4 any) | # and $XXX,%rsp |
| 165 (0x4c 0x01 0xfd) | # add %r15,%rbp | 231 (0x4c 0x01 0xfd) | # add %r15,%rbp |
| 166 (0x49 0x8d 0x2c 0x2f) | # lea (%r15,%rbp,1),%rbp | 232 (0x49 0x8d 0x2c 0x2f) | # lea (%r15,%rbp,1),%rbp |
| 167 (0x4a 0x8d 0x6c 0x3d any) | # lea 0x0(%rbp,%r15,1),%rbp | 233 (0x4a 0x8d 0x6c 0x3d any) | # lea 0x0(%rbp,%r15,1),%rbp |
| 168 (0x48 0x81 0xe5 any{4}) | # and $XXX,%rsp | 234 (0x48 0x81 0xe5 any{4}) | # and $XXX,%rsp |
| 169 (0x48 0x83 0xe5 any) | # and $XXX,%rsp | 235 (0x48 0x83 0xe5 any) | # and $XXX,%rsp |
| 170 (0x4c 0x01 0xfc) | # add %r15,%rsp | 236 (0x4c 0x01 0xfc) | # add %r15,%rsp |
| 171 (0x4a 0x8d 0x24 0x3c) | # lea (%rsp,%r15,1),%rsp | 237 (0x4a 0x8d 0x24 0x3c) | # lea (%rsp,%r15,1),%rsp |
| 172 (0x49 0x8d 0x34 0x37) | # lea (%r15,%rsi,1),%rsi | 238 (0x49 0x8d 0x34 0x37) | # lea (%r15,%rsi,1),%rsi |
| 173 (0x49 0x8d 0x3c 0x3f) # lea (%r15,%rdi,1),%rdi | 239 (0x49 0x8d 0x3c 0x3f) # lea (%r15,%rdi,1),%rdi |
| 174 )) @process_normal_instruction; | 240 ); |
| 175 | 241 |
| 176 data16condrep = (data16 | condrep data16 | data16 condrep); | 242 data16condrep = (data16 | condrep data16 | data16 condrep); |
| 177 data16rep = (data16 | rep data16 | data16 rep); | 243 data16rep = (data16 | rep data16 | data16 rep); |
| 178 | 244 |
| 179 special_instruction = | 245 special_instruction = |
| 180 (0x48 0x89 0xe5) | # mov %rsp,%rbp | 246 (0x48 0x89 0xe5) | # mov %rsp,%rbp |
| 181 (0x48 0x81 0xe4 any{3} (0x80 .. 0xff)) | # and $XXX,%rsp | 247 (0x48 0x81 0xe4 any{3} (0x80 .. 0xff)) | # and $XXX,%rsp |
| 182 (0x48 0x83 0xe4 (0x80 .. 0xff)) # and $XXX,%rsp | 248 (0x48 0x83 0xe4 (0x80 .. 0xff)) # and $XXX,%rsp |
| 183 @{ if (restricted_register == REG_RSP) { | 249 @{ if (restricted_register == REG_RSP) { |
| 184 PrintError("Incorrectly modified register %%rsp\n", begin - data); | 250 PrintError("Incorrectly modified register %%rsp\n", begin - data); |
| (...skipping 387 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 572 } | 638 } |
| 573 } | 639 } |
| 574 | 640 |
| 575 if (CheckJumpTargets(valid_targets, jump_dests, size)) { | 641 if (CheckJumpTargets(valid_targets, jump_dests, size)) { |
| 576 return 1; | 642 return 1; |
| 577 } | 643 } |
| 578 | 644 |
| 579 error_detected: | 645 error_detected: |
| 580 return result; | 646 return result; |
| 581 } | 647 } |
| OLD | NEW |