├── README.md ├── aarch64_cryptoextension.cpp ├── license.txt └── makefile /README.md: -------------------------------------------------------------------------------- 1 | # aarch64_cryptoextension 2 | IDA AArch64 processor extender extension: Adding crypto extension instructions (AES/SHA1/SHA256) 3 | -------------------------------------------------------------------------------- /aarch64_cryptoextension.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | 8 | #ifndef __EA64__ 9 | #error This extension only makes sense in a 64bit context 10 | #endif 11 | 12 | #define MAGIC_ACTIVATED 333 13 | #define MAGIC_DEACTIVATED 777 14 | 15 | static ea_t ea; 16 | 17 | inline bool is_arm64_ea(ea_t ea) 18 | { 19 | segment_t *seg = getseg(ea); 20 | return seg != NULL && seg->use64(); 21 | } 22 | 23 | #define cond segpref 24 | 25 | #define simd_sz specflag1 26 | 27 | #define cAL 14 28 | 29 | #define Q0 45 30 | #define S0 93 31 | #define V0 163 32 | 33 | static size_t ana(void) 34 | { 35 | uint32_t code = get_long(ea++); 36 | uint32_t Rn, Rd, Rm; 37 | 38 | if ((code & 0xFFFF0C00) == 0x4E280800) { 39 | Rn = (code >> 5) & 31; 40 | Rd = (code) & 31; 41 | Rd += V0; 42 | Rn += V0; 43 | if ((code & 0xF000) == 0x5000) { 44 | cmd.itype = ARM_aesd; 45 | cmd.cond = cAL; 46 | cmd.Op1.type = o_reg; 47 | cmd.Op1.simd_sz = 1; 48 | cmd.Op1.reg = Rd; 49 | cmd.Op1.dtyp = dt_byte16; 50 | cmd.Op2.type = o_reg; 51 | cmd.Op2.simd_sz = 1; 52 | cmd.Op2.reg = Rn; 53 | cmd.Op2.dtyp = dt_byte16; 54 | return 4; 55 | } else if ((code & 0xF000) == 0x4000) { 56 | cmd.itype = ARM_aese; 57 | cmd.cond = cAL; 58 | cmd.Op1.type = o_reg; 59 | cmd.Op1.simd_sz = 1; 60 | cmd.Op1.reg = Rd; 61 | cmd.Op1.dtyp = dt_byte16; 62 | cmd.Op2.type = o_reg; 63 | cmd.Op2.simd_sz = 1; 64 | cmd.Op2.reg = Rn; 65 | cmd.Op2.dtyp = dt_byte16; 66 | return 4; 67 | } else if ((code & 0xF000) == 0x7000) { 68 | cmd.itype = ARM_aesimc; 69 | cmd.cond = cAL; 70 | cmd.Op1.type = o_reg; 71 | cmd.Op1.simd_sz = 1; 72 | cmd.Op1.reg = Rd; 73 | cmd.Op1.dtyp = dt_byte16; 74 | cmd.Op2.type = o_reg; 75 | cmd.Op2.simd_sz = 1; 76 | cmd.Op2.reg = Rn; 77 | cmd.Op2.dtyp = dt_byte16; 78 | return 4; 79 | } else if ((code & 0xF000) == 0x6000) { 80 | cmd.itype = ARM_aesmc; 81 | cmd.cond = cAL; 82 | cmd.Op1.type = o_reg; 83 | cmd.Op1.simd_sz = 1; 84 | cmd.Op1.reg = Rd; 85 | cmd.Op1.dtyp = dt_byte16; 86 | cmd.Op2.type = o_reg; 87 | cmd.Op2.simd_sz = 1; 88 | cmd.Op2.reg = Rn; 89 | cmd.Op2.dtyp = dt_byte16; 90 | return 4; 91 | } 92 | } else if ((code & 0xFFE0FC00) == 0x5E000000) { 93 | Rn = (code >> 5) & 31; 94 | Rd = (code) & 31; 95 | Rm = (code >> 16) & 31; 96 | Rd += Q0; 97 | Rn += S0; 98 | Rm += V0; 99 | cmd.itype = ARM_sha1c; 100 | cmd.cond = cAL; 101 | cmd.Op1.type = o_reg; 102 | cmd.Op1.reg = Rd; 103 | cmd.Op1.dtyp = dt_byte16; 104 | cmd.Op2.type = o_reg; 105 | cmd.Op2.reg = Rn; 106 | cmd.Op2.dtyp = dt_dword; 107 | cmd.Op3.type = o_reg; 108 | cmd.Op3.simd_sz = 3; 109 | cmd.Op3.reg = Rm; 110 | cmd.Op3.dtyp = dt_byte16; 111 | return 4; 112 | } else if ((code & 0xFFFFFC00) == 0x5E280800) { 113 | Rn = (code >> 5) & 31; 114 | Rd = (code) & 31; 115 | Rd += S0; 116 | Rn += S0; 117 | cmd.itype = ARM_sha1h; 118 | cmd.cond = cAL; 119 | cmd.Op1.type = o_reg; 120 | cmd.Op1.reg = Rd; 121 | cmd.Op1.dtyp = dt_dword; 122 | cmd.Op2.type = o_reg; 123 | cmd.Op2.reg = Rn; 124 | cmd.Op2.dtyp = dt_dword; 125 | return 4; 126 | } else if ((code & 0xFFE0FC00) == 0x5E002000) { 127 | Rn = (code >> 5) & 31; 128 | Rd = (code) & 31; 129 | Rm = (code >> 16) & 31; 130 | Rd += Q0; 131 | Rn += S0; 132 | Rm += V0; 133 | cmd.itype = ARM_sha1m; 134 | cmd.cond = cAL; 135 | cmd.Op1.type = o_reg; 136 | cmd.Op1.reg = Rd; 137 | cmd.Op1.dtyp = dt_byte16; 138 | cmd.Op2.type = o_reg; 139 | cmd.Op2.reg = Rn; 140 | cmd.Op2.dtyp = dt_dword; 141 | cmd.Op3.type = o_reg; 142 | cmd.Op3.simd_sz = 3; 143 | cmd.Op3.reg = Rm; 144 | cmd.Op3.dtyp = dt_byte16; 145 | return 4; 146 | } else if ((code & 0xFFE0FC00) == 0x5E001000) { 147 | Rn = (code >> 5) & 31; 148 | Rd = (code) & 31; 149 | Rm = (code >> 16) & 31; 150 | Rd += Q0; 151 | Rn += S0; 152 | Rm += V0; 153 | cmd.itype = ARM_sha1p; 154 | cmd.cond = cAL; 155 | cmd.Op1.type = o_reg; 156 | cmd.Op1.reg = Rd; 157 | cmd.Op1.dtyp = dt_byte16; 158 | cmd.Op2.type = o_reg; 159 | cmd.Op2.reg = Rn; 160 | cmd.Op2.dtyp = dt_dword; 161 | cmd.Op3.type = o_reg; 162 | cmd.Op3.simd_sz = 3; 163 | cmd.Op3.reg = Rm; 164 | cmd.Op3.dtyp = dt_byte16; 165 | return 4; 166 | } else if ((code & 0xFFE0FC00) == 0x5E003000) { 167 | Rn = (code >> 5) & 31; 168 | Rd = (code) & 31; 169 | Rm = (code >> 16) & 31; 170 | Rd += V0; 171 | Rn += V0; 172 | Rm += V0; 173 | cmd.itype = ARM_sha1su0; 174 | cmd.cond = cAL; 175 | cmd.Op1.type = o_reg; 176 | cmd.Op1.reg = Rd; 177 | cmd.Op1.simd_sz = 3; 178 | cmd.Op1.dtyp = dt_byte16; 179 | cmd.Op2.type = o_reg; 180 | cmd.Op2.simd_sz = 3; 181 | cmd.Op2.reg = Rn; 182 | cmd.Op2.dtyp = dt_byte16; 183 | cmd.Op3.type = o_reg; 184 | cmd.Op3.simd_sz = 3; 185 | cmd.Op3.reg = Rm; 186 | cmd.Op3.dtyp = dt_byte16; 187 | return 4; 188 | } else if ((code & 0xFFFFFC00) == 0x5E281800) { 189 | Rn = (code >> 5) & 31; 190 | Rd = (code) & 31; 191 | Rd += V0; 192 | Rn += V0; 193 | cmd.itype = ARM_sha1su1; 194 | cmd.cond = cAL; 195 | cmd.Op1.type = o_reg; 196 | cmd.Op1.reg = Rd; 197 | cmd.Op1.simd_sz = 3; 198 | cmd.Op1.dtyp = dt_byte16; 199 | cmd.Op2.type = o_reg; 200 | cmd.Op2.simd_sz = 3; 201 | cmd.Op2.reg = Rn; 202 | cmd.Op2.dtyp = dt_byte16; 203 | return 4; 204 | } else if ((code & 0xFFE0FC00) == 0x5E005000) { 205 | Rn = (code >> 5) & 31; 206 | Rd = (code) & 31; 207 | Rm = (code >> 16) & 31; 208 | Rd += Q0; 209 | Rn += Q0; 210 | Rm += V0; 211 | cmd.itype = ARM_sha256h2; 212 | cmd.cond = cAL; 213 | cmd.Op1.type = o_reg; 214 | cmd.Op1.reg = Rd; 215 | cmd.Op1.dtyp = dt_byte16; 216 | cmd.Op2.type = o_reg; 217 | cmd.Op2.reg = Rn; 218 | cmd.Op2.dtyp = dt_byte16; 219 | cmd.Op3.type = o_reg; 220 | cmd.Op3.simd_sz = 3; 221 | cmd.Op3.reg = Rm; 222 | cmd.Op3.dtyp = dt_byte16; 223 | return 4; 224 | } else if ((code & 0xFFE0FC00) == 0x5E004000) { 225 | Rn = (code >> 5) & 31; 226 | Rd = (code) & 31; 227 | Rm = (code >> 16) & 31; 228 | Rd += Q0; 229 | Rn += Q0; 230 | Rm += V0; 231 | cmd.itype = ARM_sha256h; 232 | cmd.cond = cAL; 233 | cmd.Op1.type = o_reg; 234 | cmd.Op1.reg = Rd; 235 | cmd.Op1.dtyp = dt_byte16; 236 | cmd.Op2.type = o_reg; 237 | cmd.Op2.reg = Rn; 238 | cmd.Op2.dtyp = dt_byte16; 239 | cmd.Op3.type = o_reg; 240 | cmd.Op3.simd_sz = 3; 241 | cmd.Op3.reg = Rm; 242 | cmd.Op3.dtyp = dt_byte16; 243 | return 4; 244 | } else if ((code & 0xFFFFFC00) == 0x5E282800) { 245 | Rn = (code >> 5) & 31; 246 | Rd = (code) & 31; 247 | Rd += V0; 248 | Rn += V0; 249 | cmd.itype = ARM_sha256su0; 250 | cmd.cond = cAL; 251 | cmd.Op1.type = o_reg; 252 | cmd.Op1.reg = Rd; 253 | cmd.Op1.simd_sz = 3; 254 | cmd.Op1.dtyp = dt_byte16; 255 | cmd.Op2.type = o_reg; 256 | cmd.Op2.simd_sz = 3; 257 | cmd.Op2.reg = Rn; 258 | cmd.Op2.dtyp = dt_byte16; 259 | return 4; 260 | } else if ((code & 0xFFE0FC00) == 0x5E006000) { 261 | Rn = (code >> 5) & 31; 262 | Rd = (code) & 31; 263 | Rm = (code >> 16) & 31; 264 | Rd += V0; 265 | Rn += V0; 266 | Rm += V0; 267 | cmd.itype = ARM_sha256su1; 268 | cmd.cond = cAL; 269 | cmd.Op1.type = o_reg; 270 | cmd.Op1.reg = Rd; 271 | cmd.Op1.simd_sz = 3; 272 | cmd.Op1.dtyp = dt_byte16; 273 | cmd.Op2.type = o_reg; 274 | cmd.Op2.simd_sz = 3; 275 | cmd.Op2.reg = Rn; 276 | cmd.Op2.dtyp = dt_byte16; 277 | cmd.Op3.type = o_reg; 278 | cmd.Op3.simd_sz = 3; 279 | cmd.Op3.reg = Rm; 280 | cmd.Op3.dtyp = dt_byte16; 281 | return 4; 282 | } 283 | return 0; 284 | } 285 | 286 | static int idaapi aarch64_extension_callback(void * user_data, int event_id, va_list va) 287 | { 288 | switch (event_id) 289 | { 290 | case processor_t::custom_ana: 291 | { 292 | ea = cmd.ea; 293 | if (is_arm64_ea(ea)) { 294 | size_t length = ana(); 295 | if (length) 296 | { 297 | cmd.size = (uint16)length; 298 | return 2; 299 | } 300 | } 301 | } 302 | break; 303 | } 304 | return 0; 305 | } 306 | 307 | static bool enabled = false; 308 | static netnode aarch64_node; 309 | static const char node_name[] = "$ AArch64 crypto extension processor extender parameters"; 310 | 311 | int idaapi init(void) 312 | { 313 | if (ph.id != PLFM_ARM) return PLUGIN_SKIP; 314 | aarch64_node.create(node_name); 315 | enabled = aarch64_node.altval(0) != MAGIC_DEACTIVATED; 316 | if (enabled) 317 | { 318 | hook_to_notification_point(HT_IDP, aarch64_extension_callback, NULL); 319 | msg("AArch64 crypto extension processor extender is enabled\n"); 320 | return PLUGIN_KEEP; 321 | } 322 | return PLUGIN_OK; 323 | } 324 | 325 | 326 | void idaapi term(void) 327 | { 328 | unhook_from_notification_point(HT_IDP, aarch64_extension_callback); 329 | } 330 | 331 | void idaapi run(int /*arg*/) 332 | { 333 | if (enabled) { 334 | unhook_from_notification_point(HT_IDP, aarch64_extension_callback); 335 | } else { 336 | hook_to_notification_point(HT_IDP, aarch64_extension_callback, NULL); 337 | } 338 | enabled = !enabled; 339 | aarch64_node.create(node_name); 340 | aarch64_node.altset(0, enabled ? MAGIC_ACTIVATED : MAGIC_DEACTIVATED); 341 | info("AUTOHIDE NONE\n" "AArch64 crypto extension processor extender now is %s", enabled ? "enabled" : "disabled"); 342 | } 343 | 344 | //-------------------------------------------------------------------------- 345 | static const char comment[] = "AArch64 crypto extension processor extender"; 346 | static const char help[] = "This module adds support for AArch64 crypto extension instructions to IDA.\n"; 347 | 348 | static const char wanted_name[] = "AArch64 crypto extension processor extender"; 349 | 350 | static const char wanted_hotkey[] = ""; 351 | 352 | plugin_t PLUGIN = 353 | { 354 | IDP_INTERFACE_VERSION, 355 | PLUGIN_PROC, 356 | init, 357 | term, 358 | run, 359 | comment, 360 | help, 361 | wanted_name, 362 | wanted_hotkey 363 | }; 364 | -------------------------------------------------------------------------------- /license.txt: -------------------------------------------------------------------------------- 1 | The code of aarch64_cryptoextension is 2 | (C) Copyright 2015-2016 SektionEins GmbH 3 | and has been authored by Stefan Esser 4 | 5 | The code is provided for educational purposes and to allow 6 | recompilation with new versions of the IDASDK. 7 | 8 | The code is not and was never licensed under a free/open 9 | source license. You are NOT free to just copy the code 10 | and put it into your own projects be it commercial or 11 | non commercial nature. 12 | -------------------------------------------------------------------------------- /makefile: -------------------------------------------------------------------------------- 1 | PROC=aarch64_cryptoextension 2 | include ../plugin.mak 3 | 4 | # MAKEDEP dependency list ------------------ 5 | $(F)aarch64_cryptoextension$(O) : $(I)area.hpp $(I)bitrange.hpp $(I)bytes.hpp $(I)fpro.h \ 6 | $(I)funcs.hpp $(I)ida.hpp $(I)idp.hpp $(I)kernwin.hpp \ 7 | $(I)lines.hpp $(I)llong.hpp $(I)loader.hpp $(I)nalt.hpp \ 8 | $(I)netnode.hpp $(I)pro.h $(I)segment.hpp $(I)ua.hpp \ 9 | $(I)xref.hpp aarch64_cryptoextension.cpp 10 | --------------------------------------------------------------------------------