1/* Machine description patterns for PowerPC running Darwin (Mac OS X). 2 Copyright (C) 2004, 2005 Free Software Foundation, Inc. 3 Contributed by Apple Computer Inc. 4 5This file is part of GCC. 6 7GNU CC is free software; you can redistribute it and/or modify 8it under the terms of the GNU General Public License as published by 9the Free Software Foundation; either version 2, or (at your option) 10any later version. 11 12GNU CC is distributed in the hope that it will be useful, 13but WITHOUT ANY WARRANTY; without even the implied warranty of 14MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 15GNU General Public License for more details. 16 17You should have received a copy of the GNU General Public License 18along with GNU CC; see the file COPYING. If not, write to 19the Free Software Foundation, 51 Franklin Street, Fifth Floor, 20Boston, MA 02110-1301, USA. */ 21 22(define_insn "adddi3_high" 23 [(set (match_operand:DI 0 "gpc_reg_operand" "=b") 24 (plus:DI (match_operand:DI 1 "gpc_reg_operand" "b") 25 (high:DI (match_operand 2 "" ""))))] 26 "TARGET_MACHO && TARGET_64BIT" 27 "{cau|addis} %0,%1,ha16(%2)" 28 [(set_attr "length" "4")]) 29 30(define_insn "movdf_low_si" 31 [(set (match_operand:DF 0 "gpc_reg_operand" "=f,!r") 32 (mem:DF (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b,b") 33 (match_operand 2 "" ""))))] 34 "TARGET_MACHO && TARGET_HARD_FLOAT && TARGET_FPRS && !TARGET_64BIT" 35 "* 36{ 37 switch (which_alternative) 38 { 39 case 0: 40 return \"lfd %0,lo16(%2)(%1)\"; 41 case 1: 42 { 43 if (TARGET_POWERPC64 && TARGET_32BIT) 44 /* Note, old assemblers didn't support relocation here. */ 45 return \"ld %0,lo16(%2)(%1)\"; 46 else 47 { 48 output_asm_insn (\"{cal|la} %0,lo16(%2)(%1)\", operands); 49 output_asm_insn (\"{l|lwz} %L0,4(%0)\", operands); 50 return (\"{l|lwz} %0,0(%0)\"); 51 } 52 } 53 default: 54 gcc_unreachable (); 55 } 56}" 57 [(set_attr "type" "load") 58 (set_attr "length" "4,12")]) 59 60 61(define_insn "movdf_low_di" 62 [(set (match_operand:DF 0 "gpc_reg_operand" "=f,!r") 63 (mem:DF (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b,b") 64 (match_operand 2 "" ""))))] 65 "TARGET_MACHO && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_64BIT" 66 "* 67{ 68 switch (which_alternative) 69 { 70 case 0: 71 return \"lfd %0,lo16(%2)(%1)\"; 72 case 1: 73 return \"ld %0,lo16(%2)(%1)\"; 74 default: 75 gcc_unreachable (); 76 } 77}" 78 [(set_attr "type" "load") 79 (set_attr "length" "4,4")]) 80 81(define_insn "movdf_low_st_si" 82 [(set (mem:DF (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b") 83 (match_operand 2 "" ""))) 84 (match_operand:DF 0 "gpc_reg_operand" "f"))] 85 "TARGET_MACHO && TARGET_HARD_FLOAT && TARGET_FPRS && ! TARGET_64BIT" 86 "stfd %0,lo16(%2)(%1)" 87 [(set_attr "type" "store") 88 (set_attr "length" "4")]) 89 90(define_insn "movdf_low_st_di" 91 [(set (mem:DF (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b") 92 (match_operand 2 "" ""))) 93 (match_operand:DF 0 "gpc_reg_operand" "f"))] 94 "TARGET_MACHO && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_64BIT" 95 "stfd %0,lo16(%2)(%1)" 96 [(set_attr "type" "store") 97 (set_attr "length" "4")]) 98 99(define_insn "movsf_low_si" 100 [(set (match_operand:SF 0 "gpc_reg_operand" "=f,!r") 101 (mem:SF (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b,b") 102 (match_operand 2 "" ""))))] 103 "TARGET_MACHO && TARGET_HARD_FLOAT && TARGET_FPRS && ! TARGET_64BIT" 104 "@ 105 lfs %0,lo16(%2)(%1) 106 {l|lwz} %0,lo16(%2)(%1)" 107 [(set_attr "type" "load") 108 (set_attr "length" "4")]) 109 110(define_insn "movsf_low_di" 111 [(set (match_operand:SF 0 "gpc_reg_operand" "=f,!r") 112 (mem:SF (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b,b") 113 (match_operand 2 "" ""))))] 114 "TARGET_MACHO && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_64BIT" 115 "@ 116 lfs %0,lo16(%2)(%1) 117 {l|lwz} %0,lo16(%2)(%1)" 118 [(set_attr "type" "load") 119 (set_attr "length" "4")]) 120 121(define_insn "movsf_low_st_si" 122 [(set (mem:SF (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b,b") 123 (match_operand 2 "" ""))) 124 (match_operand:SF 0 "gpc_reg_operand" "f,!r"))] 125 "TARGET_MACHO && TARGET_HARD_FLOAT && TARGET_FPRS && ! TARGET_64BIT" 126 "@ 127 stfs %0,lo16(%2)(%1) 128 {st|stw} %0,lo16(%2)(%1)" 129 [(set_attr "type" "store") 130 (set_attr "length" "4")]) 131 132(define_insn "movsf_low_st_di" 133 [(set (mem:SF (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b,b") 134 (match_operand 2 "" ""))) 135 (match_operand:SF 0 "gpc_reg_operand" "f,!r"))] 136 "TARGET_MACHO && TARGET_HARD_FLOAT && TARGET_FPRS && TARGET_64BIT" 137 "@ 138 stfs %0,lo16(%2)(%1) 139 {st|stw} %0,lo16(%2)(%1)" 140 [(set_attr "type" "store") 141 (set_attr "length" "4")]) 142 143;; 64-bit MachO load/store support 144(define_insn "movdi_low" 145 [(set (match_operand:DI 0 "gpc_reg_operand" "=r") 146 (mem:DI (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b") 147 (match_operand 2 "" ""))))] 148 "TARGET_MACHO && TARGET_64BIT" 149 "{l|ld} %0,lo16(%2)(%1)" 150 [(set_attr "type" "load") 151 (set_attr "length" "4")]) 152 153(define_insn "movsi_low_st" 154 [(set (mem:SI (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b") 155 (match_operand 2 "" ""))) 156 (match_operand:SI 0 "gpc_reg_operand" "r"))] 157 "TARGET_MACHO && ! TARGET_64BIT" 158 "{st|stw} %0,lo16(%2)(%1)" 159 [(set_attr "type" "store") 160 (set_attr "length" "4")]) 161 162(define_insn "movdi_low_st" 163 [(set (mem:DI (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b") 164 (match_operand 2 "" ""))) 165 (match_operand:DI 0 "gpc_reg_operand" "r"))] 166 "TARGET_MACHO && TARGET_64BIT" 167 "{st|std} %0,lo16(%2)(%1)" 168 [(set_attr "type" "store") 169 (set_attr "length" "4")]) 170 171;; Mach-O PIC trickery. 172(define_expand "macho_high" 173 [(set (match_operand 0 "" "") 174 (high (match_operand 1 "" "")))] 175 "TARGET_MACHO" 176{ 177 if (TARGET_64BIT) 178 emit_insn (gen_macho_high_di (operands[0], operands[1])); 179 else 180 emit_insn (gen_macho_high_si (operands[0], operands[1])); 181 182 DONE; 183}) 184 185(define_insn "macho_high_si" 186 [(set (match_operand:SI 0 "gpc_reg_operand" "=b*r") 187 (high:SI (match_operand 1 "" "")))] 188 "TARGET_MACHO && ! TARGET_64BIT" 189 "{liu|lis} %0,ha16(%1)") 190 191 192(define_insn "macho_high_di" 193 [(set (match_operand:DI 0 "gpc_reg_operand" "=b*r") 194 (high:DI (match_operand 1 "" "")))] 195 "TARGET_MACHO && TARGET_64BIT" 196 "{liu|lis} %0,ha16(%1)") 197 198(define_expand "macho_low" 199 [(set (match_operand 0 "" "") 200 (lo_sum (match_operand 1 "" "") 201 (match_operand 2 "" "")))] 202 "TARGET_MACHO" 203{ 204 if (TARGET_64BIT) 205 emit_insn (gen_macho_low_di (operands[0], operands[1], operands[2])); 206 else 207 emit_insn (gen_macho_low_si (operands[0], operands[1], operands[2])); 208 209 DONE; 210}) 211 212(define_insn "macho_low_si" 213 [(set (match_operand:SI 0 "gpc_reg_operand" "=r,r") 214 (lo_sum:SI (match_operand:SI 1 "gpc_reg_operand" "b,!*r") 215 (match_operand 2 "" "")))] 216 "TARGET_MACHO && ! TARGET_64BIT" 217 "@ 218 {cal %0,%a2@l(%1)|la %0,lo16(%2)(%1)} 219 {cal %0,%a2@l(%1)|addic %0,%1,lo16(%2)}") 220 221(define_insn "macho_low_di" 222 [(set (match_operand:DI 0 "gpc_reg_operand" "=r,r") 223 (lo_sum:DI (match_operand:DI 1 "gpc_reg_operand" "b,!*r") 224 (match_operand 2 "" "")))] 225 "TARGET_MACHO && TARGET_64BIT" 226 "@ 227 {cal %0,%a2@l(%1)|la %0,lo16(%2)(%1)} 228 {cal %0,%a2@l(%1)|addic %0,%1,lo16(%2)}") 229 230(define_split 231 [(set (mem:V4SI (plus:DI (match_operand:DI 0 "gpc_reg_operand" "") 232 (match_operand:DI 1 "short_cint_operand" ""))) 233 (match_operand:V4SI 2 "register_operand" "")) 234 (clobber (match_operand:DI 3 "gpc_reg_operand" ""))] 235 "TARGET_MACHO && TARGET_64BIT" 236 [(set (match_dup 3) (plus:DI (match_dup 0) (match_dup 1))) 237 (set (mem:V4SI (match_dup 3)) 238 (match_dup 2))] 239 "") 240 241(define_expand "load_macho_picbase" 242 [(set (match_operand 0 "" "") 243 (unspec [(match_operand 1 "" "")] 244 UNSPEC_LD_MPIC))] 245 "(DEFAULT_ABI == ABI_DARWIN) && flag_pic" 246{ 247 if (TARGET_32BIT) 248 emit_insn (gen_load_macho_picbase_si (operands[0], operands[1])); 249 else 250 emit_insn (gen_load_macho_picbase_di (operands[0], operands[1])); 251 252 DONE; 253}) 254 255(define_insn "load_macho_picbase_si" 256 [(set (match_operand:SI 0 "register_operand" "=l") 257 (unspec:SI [(match_operand:SI 1 "immediate_operand" "s") 258 (pc)] UNSPEC_LD_MPIC))] 259 "(DEFAULT_ABI == ABI_DARWIN) && flag_pic" 260 "bcl 20,31,%1\\n%1:" 261 [(set_attr "type" "branch") 262 (set_attr "length" "4")]) 263 264(define_insn "load_macho_picbase_di" 265 [(set (match_operand:DI 0 "register_operand" "=l") 266 (unspec:DI [(match_operand:DI 1 "immediate_operand" "s") 267 (pc)] UNSPEC_LD_MPIC))] 268 "(DEFAULT_ABI == ABI_DARWIN) && flag_pic && TARGET_64BIT" 269 "bcl 20,31,%1\\n%1:" 270 [(set_attr "type" "branch") 271 (set_attr "length" "4")]) 272 273(define_expand "macho_correct_pic" 274 [(set (match_operand 0 "" "") 275 (plus (match_operand 1 "" "") 276 (unspec [(match_operand 2 "" "") 277 (match_operand 3 "" "")] 278 UNSPEC_MPIC_CORRECT)))] 279 "DEFAULT_ABI == ABI_DARWIN" 280{ 281 if (TARGET_32BIT) 282 emit_insn (gen_macho_correct_pic_si (operands[0], operands[1], operands[2], 283 operands[3])); 284 else 285 emit_insn (gen_macho_correct_pic_di (operands[0], operands[1], operands[2], 286 operands[3])); 287 288 DONE; 289}) 290 291(define_insn "macho_correct_pic_si" 292 [(set (match_operand:SI 0 "gpc_reg_operand" "=r") 293 (plus:SI (match_operand:SI 1 "gpc_reg_operand" "r") 294 (unspec:SI [(match_operand:SI 2 "immediate_operand" "s") 295 (match_operand:SI 3 "immediate_operand" "s")] 296 UNSPEC_MPIC_CORRECT)))] 297 "DEFAULT_ABI == ABI_DARWIN" 298 "addis %0,%1,ha16(%2-%3)\n\taddi %0,%0,lo16(%2-%3)" 299 [(set_attr "length" "8")]) 300 301(define_insn "macho_correct_pic_di" 302 [(set (match_operand:DI 0 "gpc_reg_operand" "=r") 303 (plus:DI (match_operand:DI 1 "gpc_reg_operand" "r") 304 (unspec:DI [(match_operand:DI 2 "immediate_operand" "s") 305 (match_operand:DI 3 "immediate_operand" "s")] 306 16)))] 307 "DEFAULT_ABI == ABI_DARWIN && TARGET_64BIT" 308 "addis %0,%1,ha16(%2-%3)\n\taddi %0,%0,lo16(%2-%3)" 309 [(set_attr "length" "8")]) 310 311(define_insn "*call_indirect_nonlocal_darwin64" 312 [(call (mem:SI (match_operand:DI 0 "register_operand" "c,*l,c,*l")) 313 (match_operand 1 "" "g,g,g,g")) 314 (use (match_operand:SI 2 "immediate_operand" "O,O,n,n")) 315 (clobber (match_scratch:SI 3 "=l,l,l,l"))] 316 "DEFAULT_ABI == ABI_DARWIN && TARGET_64BIT" 317{ 318 return "b%T0l"; 319} 320 [(set_attr "type" "jmpreg,jmpreg,jmpreg,jmpreg") 321 (set_attr "length" "4,4,8,8")]) 322 323(define_insn "*call_nonlocal_darwin64" 324 [(call (mem:SI (match_operand:DI 0 "symbol_ref_operand" "s,s")) 325 (match_operand 1 "" "g,g")) 326 (use (match_operand:SI 2 "immediate_operand" "O,n")) 327 (clobber (match_scratch:SI 3 "=l,l"))] 328 "(DEFAULT_ABI == ABI_DARWIN) 329 && (INTVAL (operands[2]) & CALL_LONG) == 0" 330{ 331#if TARGET_MACHO 332 return output_call(insn, operands, 0, 2); 333#else 334 gcc_unreachable (); 335#endif 336} 337 [(set_attr "type" "branch,branch") 338 (set_attr "length" "4,8")]) 339 340(define_insn "*call_value_indirect_nonlocal_darwin64" 341 [(set (match_operand 0 "" "") 342 (call (mem:SI (match_operand:DI 1 "register_operand" "c,*l,c,*l")) 343 (match_operand 2 "" "g,g,g,g"))) 344 (use (match_operand:SI 3 "immediate_operand" "O,O,n,n")) 345 (clobber (match_scratch:SI 4 "=l,l,l,l"))] 346 "DEFAULT_ABI == ABI_DARWIN" 347{ 348 return "b%T1l"; 349} 350 [(set_attr "type" "jmpreg,jmpreg,jmpreg,jmpreg") 351 (set_attr "length" "4,4,8,8")]) 352 353(define_insn "*call_value_nonlocal_darwin64" 354 [(set (match_operand 0 "" "") 355 (call (mem:SI (match_operand:DI 1 "symbol_ref_operand" "s,s")) 356 (match_operand 2 "" "g,g"))) 357 (use (match_operand:SI 3 "immediate_operand" "O,n")) 358 (clobber (match_scratch:SI 4 "=l,l"))] 359 "(DEFAULT_ABI == ABI_DARWIN) 360 && (INTVAL (operands[3]) & CALL_LONG) == 0" 361{ 362#if TARGET_MACHO 363 return output_call(insn, operands, 1, 3); 364#else 365 gcc_unreachable (); 366#endif 367} 368 [(set_attr "type" "branch,branch") 369 (set_attr "length" "4,8")]) 370 371(define_insn "*sibcall_nonlocal_darwin64" 372 [(call (mem:SI (match_operand:DI 0 "symbol_ref_operand" "s,s")) 373 (match_operand 1 "" "")) 374 (use (match_operand 2 "immediate_operand" "O,n")) 375 (use (match_operand:SI 3 "register_operand" "l,l")) 376 (return)] 377 "(DEFAULT_ABI == ABI_DARWIN) 378 && (INTVAL (operands[2]) & CALL_LONG) == 0" 379{ 380 return "b %z0"; 381} 382 [(set_attr "type" "branch,branch") 383 (set_attr "length" "4,8")]) 384 385(define_insn "*sibcall_value_nonlocal_darwin64" 386 [(set (match_operand 0 "" "") 387 (call (mem:SI (match_operand:DI 1 "symbol_ref_operand" "s,s")) 388 (match_operand 2 "" ""))) 389 (use (match_operand:SI 3 "immediate_operand" "O,n")) 390 (use (match_operand:SI 4 "register_operand" "l,l")) 391 (return)] 392 "(DEFAULT_ABI == ABI_DARWIN) 393 && (INTVAL (operands[3]) & CALL_LONG) == 0" 394 "* 395{ 396 return \"b %z1\"; 397}" 398 [(set_attr "type" "branch,branch") 399 (set_attr "length" "4,8")]) 400 401 402(define_insn "*sibcall_symbolic_64" 403 [(call (mem:SI (match_operand:DI 0 "call_operand" "s,c")) ; 64 404 (match_operand 1 "" "")) 405 (use (match_operand 2 "" "")) 406 (use (match_operand:SI 3 "register_operand" "l,l")) 407 (return)] 408 "TARGET_64BIT && DEFAULT_ABI == ABI_DARWIN" 409 "* 410{ 411 switch (which_alternative) 412 { 413 case 0: return \"b %z0\"; 414 case 1: return \"b%T0\"; 415 default: gcc_unreachable (); 416 } 417}" 418 [(set_attr "type" "branch") 419 (set_attr "length" "4")]) 420 421(define_insn "*sibcall_value_symbolic_64" 422 [(set (match_operand 0 "" "") 423 (call (mem:SI (match_operand:DI 1 "call_operand" "s,c")) 424 (match_operand 2 "" ""))) 425 (use (match_operand:SI 3 "" "")) 426 (use (match_operand:SI 4 "register_operand" "l,l")) 427 (return)] 428 "TARGET_64BIT && DEFAULT_ABI == ABI_DARWIN" 429 "* 430{ 431 switch (which_alternative) 432 { 433 case 0: return \"b %z1\"; 434 case 1: return \"b%T1\"; 435 default: gcc_unreachable (); 436 } 437}" 438 [(set_attr "type" "branch") 439 (set_attr "length" "4")]) 440 441