OLD | NEW |
1 // Copyright (c) 1994-2006 Sun Microsystems Inc. | 1 // Copyright (c) 1994-2006 Sun Microsystems Inc. |
2 // All Rights Reserved. | 2 // All Rights Reserved. |
3 // | 3 // |
4 // Redistribution and use in source and binary forms, with or without | 4 // Redistribution and use in source and binary forms, with or without |
5 // modification, are permitted provided that the following conditions | 5 // modification, are permitted provided that the following conditions |
6 // are met: | 6 // are met: |
7 // | 7 // |
8 // - Redistributions of source code must retain the above copyright notice, | 8 // - Redistributions of source code must retain the above copyright notice, |
9 // this list of conditions and the following disclaimer. | 9 // this list of conditions and the following disclaimer. |
10 // | 10 // |
(...skipping 828 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
839 void blx(Label* L) { blx(branch_offset(L, false)); } // v5 and above | 839 void blx(Label* L) { blx(branch_offset(L, false)); } // v5 and above |
840 | 840 |
841 // Data-processing instructions | 841 // Data-processing instructions |
842 | 842 |
843 void and_(Register dst, Register src1, const Operand& src2, | 843 void and_(Register dst, Register src1, const Operand& src2, |
844 SBit s = LeaveCC, Condition cond = al); | 844 SBit s = LeaveCC, Condition cond = al); |
845 void and_imm_t1(Register dst, Register src1, SBit s, Condition cond, | 845 void and_imm_t1(Register dst, Register src1, SBit s, Condition cond, |
846 uint32_t i, uint32_t imm3, uint32_t imm8); | 846 uint32_t i, uint32_t imm3, uint32_t imm8); |
847 void and_reg_t2(Register dst, Register src1, const Operand& src2, | 847 void and_reg_t2(Register dst, Register src1, const Operand& src2, |
848 SBit s, Condition cond); | 848 SBit s, Condition cond); |
| 849 void and_thumb(Register dst, Register src1, const Operand& src2, |
| 850 SBit s, Condition cond); |
849 | 851 |
850 void eor(Register dst, Register src1, const Operand& src2, | 852 void eor(Register dst, Register src1, const Operand& src2, |
851 SBit s = LeaveCC, Condition cond = al); | 853 SBit s = LeaveCC, Condition cond = al); |
852 void eor_imm_t1(Register dst, Register src1, SBit s, Condition cond, | 854 void eor_imm_t1(Register dst, Register src1, SBit s, Condition cond, |
853 uint32_t i, uint32_t imm3, uint32_t imm8); | 855 uint32_t i, uint32_t imm3, uint32_t imm8); |
854 void eor_reg_t2(Register dst, Register src1, const Operand& src2, | 856 void eor_reg_t2(Register dst, Register src1, const Operand& src2, |
855 SBit s, Condition cond); | 857 SBit s, Condition cond); |
| 858 void eor_thumb(Register dst, Register src1, const Operand& src2, |
| 859 SBit s, Condition cond); |
856 | 860 |
857 void sub(Register dst, Register src1, const Operand& src2, | 861 void sub(Register dst, Register src1, const Operand& src2, |
858 SBit s = LeaveCC, Condition cond = al); | 862 SBit s = LeaveCC, Condition cond = al); |
859 void sub(Register dst, Register src1, Register src2, | 863 void sub(Register dst, Register src1, Register src2, |
860 SBit s = LeaveCC, Condition cond = al) { | 864 SBit s = LeaveCC, Condition cond = al) { |
861 sub(dst, src1, Operand(src2), s, cond); | 865 sub(dst, src1, Operand(src2), s, cond); |
862 } | 866 } |
863 void sub_imm_t3(Register dst, Register src1, SBit s, Condition cond, | 867 void sub_imm_t3(Register dst, Register src1, SBit s, Condition cond, |
864 uint32_t i, uint32_t imm3, uint32_t imm8); | 868 uint32_t i, uint32_t imm3, uint32_t imm8); |
865 void sub_imm_t4(Register dst, Register src1, const Operand& src2, | 869 void sub_imm_t4(Register dst, Register src1, const Operand& src2, |
866 SBit s, Condition cond); | 870 SBit s, Condition cond); |
867 void sub_reg_t3(Register dst, Register src1, const Operand& src2, | 871 void sub_reg_t3(Register dst, Register src1, const Operand& src2, |
868 SBit s, Condition cond); | 872 SBit s, Condition cond); |
| 873 void sub_thumb(Register dst, Register src1, const Operand& src2, |
| 874 SBit s, Condition cond); |
869 | 875 |
870 void rsb(Register dst, Register src1, const Operand& src2, | 876 void rsb(Register dst, Register src1, const Operand& src2, |
871 SBit s = LeaveCC, Condition cond = al); | 877 SBit s = LeaveCC, Condition cond = al); |
872 void rsb_imm_t2(Register dst, Register src1, SBit s, Condition cond, | 878 void rsb_imm_t2(Register dst, Register src1, SBit s, Condition cond, |
873 uint32_t i, uint32_t imm3, uint32_t imm8); | 879 uint32_t i, uint32_t imm3, uint32_t imm8); |
874 void rsb_reg_t1(Register dst, Register src1, const Operand& src2, | 880 void rsb_reg_t1(Register dst, Register src1, const Operand& src2, |
875 SBit s, Condition cond); | 881 SBit s, Condition cond); |
| 882 void rsb_thumb(Register dst, Register src1, const Operand& src2, |
| 883 SBit s, Condition cond); |
876 | 884 |
877 void add(Register dst, Register src1, const Operand& src2, | 885 void add(Register dst, Register src1, const Operand& src2, |
878 SBit s = LeaveCC, Condition cond = al); | 886 SBit s = LeaveCC, Condition cond = al); |
879 void add(Register dst, Register src1, Register src2, | 887 void add(Register dst, Register src1, Register src2, |
880 SBit s = LeaveCC, Condition cond = al) { | 888 SBit s = LeaveCC, Condition cond = al) { |
881 add(dst, src1, Operand(src2), s, cond); | 889 add(dst, src1, Operand(src2), s, cond); |
882 } | 890 } |
883 void add_imm_t3(Register dst, Register src1, SBit s, Condition cond, | 891 void add_imm_t3(Register dst, Register src1, SBit s, Condition cond, |
884 uint32_t i, uint32_t imm3, uint32_t imm8); | 892 uint32_t i, uint32_t imm3, uint32_t imm8); |
885 void add_imm_t4(Register dst, Register src1, const Operand& src2, | 893 void add_imm_t4(Register dst, Register src1, const Operand& src2, |
886 SBit s, Condition cond); | 894 SBit s, Condition cond); |
887 void add_reg_t3(Register dst, Register src1, const Operand& src2, | 895 void add_reg_t3(Register dst, Register src1, const Operand& src2, |
888 SBit s, Condition cond); | 896 SBit s, Condition cond); |
| 897 void add_thumb(Register dst, Register src1, const Operand& src2, |
| 898 SBit s, Condition cond); |
889 | 899 |
890 void adc(Register dst, Register src1, const Operand& src2, | 900 void adc(Register dst, Register src1, const Operand& src2, |
891 SBit s = LeaveCC, Condition cond = al); | 901 SBit s = LeaveCC, Condition cond = al); |
892 void adc_imm_t1(Register dst, Register src1, SBit s, Condition cond, | 902 void adc_imm_t1(Register dst, Register src1, SBit s, Condition cond, |
893 uint32_t i, uint32_t imm3, uint32_t imm8); | 903 uint32_t i, uint32_t imm3, uint32_t imm8); |
894 void adc_reg_t2(Register dst, Register src1, const Operand& src2, | 904 void adc_reg_t2(Register dst, Register src1, const Operand& src2, |
895 SBit s, Condition cond); | 905 SBit s, Condition cond); |
| 906 void adc_thumb(Register dst, Register src1, const Operand& src2, |
| 907 SBit s, Condition cond); |
896 | 908 |
897 void sbc(Register dst, Register src1, const Operand& src2, | 909 void sbc(Register dst, Register src1, const Operand& src2, |
898 SBit s = LeaveCC, Condition cond = al); | 910 SBit s = LeaveCC, Condition cond = al); |
899 void sbc_imm_t1(Register dst, Register src1, SBit s, Condition cond, | 911 void sbc_imm_t1(Register dst, Register src1, SBit s, Condition cond, |
900 uint32_t i, uint32_t imm3, uint32_t imm8); | 912 uint32_t i, uint32_t imm3, uint32_t imm8); |
901 void sbc_reg_t2(Register dst, Register src1, const Operand& src2, | 913 void sbc_reg_t2(Register dst, Register src1, const Operand& src2, |
902 SBit s, Condition cond); | 914 SBit s, Condition cond); |
| 915 void sbc_thumb(Register dst, Register src1, const Operand& src2, |
| 916 SBit s, Condition cond); |
903 | 917 |
904 void rsc(Register dst, Register src1, const Operand& src2, | 918 void rsc(Register dst, Register src1, const Operand& src2, |
905 SBit s = LeaveCC, Condition cond = al); | 919 SBit s = LeaveCC, Condition cond = al); |
906 | 920 |
907 void tst(Register src1, const Operand& src2, Condition cond = al); | 921 void tst(Register src1, const Operand& src2, Condition cond = al); |
908 void tst(Register src1, Register src2, Condition cond = al) { | 922 void tst(Register src1, Register src2, Condition cond = al) { |
909 tst(src1, Operand(src2), cond); | 923 tst(src1, Operand(src2), cond); |
910 } | 924 } |
911 void tst_imm_t1(Register src1, Condition cond, | 925 void tst_imm_t1(Register src1, Condition cond, |
912 uint32_t i, uint32_t imm3, uint32_t imm8); | 926 uint32_t i, uint32_t imm3, uint32_t imm8); |
913 void tst_reg_t2(Register src1, const Operand& src2, Condition cond); | 927 void tst_reg_t2(Register src1, const Operand& src2, Condition cond); |
| 928 void tst_thumb(Register src1, const Operand& src2, Condition cond); |
914 | 929 |
915 void teq(Register src1, const Operand& src2, Condition cond = al); | 930 void teq(Register src1, const Operand& src2, Condition cond = al); |
916 void teq_imm_t1(Register src1, Condition cond, | 931 void teq_imm_t1(Register src1, Condition cond, |
917 uint32_t i, uint32_t imm3, uint32_t imm8); | 932 uint32_t i, uint32_t imm3, uint32_t imm8); |
918 void teq_reg_t1(Register src1, const Operand& src2, Condition cond); | 933 void teq_reg_t1(Register src1, const Operand& src2, Condition cond); |
| 934 void teq_thumb(Register src1, const Operand& src2, Condition cond); |
919 | 935 |
920 void cmp(Register src1, const Operand& src2, Condition cond = al); | 936 void cmp(Register src1, const Operand& src2, Condition cond = al); |
921 void cmp(Register src1, Register src2, Condition cond = al) { | 937 void cmp(Register src1, Register src2, Condition cond = al) { |
922 cmp(src1, Operand(src2), cond); | 938 cmp(src1, Operand(src2), cond); |
923 } | 939 } |
924 void cmp_imm_t2(Register src1, Condition cond, | 940 void cmp_imm_t2(Register src1, Condition cond, |
925 uint32_t i, uint32_t imm3, uint32_t imm8); | 941 uint32_t i, uint32_t imm3, uint32_t imm8); |
926 void cmp_reg_t3(Register src1, const Operand& src2, Condition cond); | 942 void cmp_reg_t3(Register src1, const Operand& src2, Condition cond); |
| 943 void cmp_thumb(Register src1, const Operand& src2, Condition cond); |
927 void cmp_raw_immediate(Register src1, int raw_immediate, Condition cond = al); | 944 void cmp_raw_immediate(Register src1, int raw_immediate, Condition cond = al); |
928 | 945 |
929 void cmn(Register src1, const Operand& src2, Condition cond = al); | 946 void cmn(Register src1, const Operand& src2, Condition cond = al); |
930 void cmn_imm_t1(Register src1, Condition cond, | 947 void cmn_imm_t1(Register src1, Condition cond, |
931 uint32_t i, uint32_t imm3, uint32_t imm8); | 948 uint32_t i, uint32_t imm3, uint32_t imm8); |
932 void cmn_reg_t2(Register src1, const Operand& src2, Condition cond); | 949 void cmn_reg_t2(Register src1, const Operand& src2, Condition cond); |
| 950 void cmn_thumb(Register src1, const Operand& src2, Condition cond); |
933 | 951 |
934 void orr(Register dst, Register src1, const Operand& src2, | 952 void orr(Register dst, Register src1, const Operand& src2, |
935 SBit s = LeaveCC, Condition cond = al); | 953 SBit s = LeaveCC, Condition cond = al); |
936 void orr(Register dst, Register src1, Register src2, | 954 void orr(Register dst, Register src1, Register src2, |
937 SBit s = LeaveCC, Condition cond = al) { | 955 SBit s = LeaveCC, Condition cond = al) { |
938 orr(dst, src1, Operand(src2), s, cond); | 956 orr(dst, src1, Operand(src2), s, cond); |
939 } | 957 } |
940 void orr_imm_t1(Register dst, Register src1, SBit s, Condition cond, | 958 void orr_imm_t1(Register dst, Register src1, SBit s, Condition cond, |
941 uint32_t i, uint32_t imm3, uint32_t imm8); | 959 uint32_t i, uint32_t imm3, uint32_t imm8); |
942 void orr_reg_t2(Register dst, Register src1, const Operand& src2, | 960 void orr_reg_t2(Register dst, Register src1, const Operand& src2, |
943 SBit s, Condition cond); | 961 SBit s, Condition cond); |
| 962 void orr_thumb(Register dst, Register src1, const Operand& src2, |
| 963 SBit s, Condition cond); |
944 | 964 |
945 void mov(Register dst, const Operand& src, | 965 void mov(Register dst, const Operand& src, |
946 SBit s = LeaveCC, Condition cond = al); | 966 SBit s = LeaveCC, Condition cond = al); |
947 void mov(Register dst, Register src, SBit s = LeaveCC, Condition cond = al) { | 967 void mov(Register dst, Register src, SBit s = LeaveCC, Condition cond = al) { |
948 mov(dst, Operand(src), s, cond); | 968 mov(dst, Operand(src), s, cond); |
949 } | 969 } |
950 void mov_imm_t2(Register dst, SBit s, Condition cond, | 970 void mov_imm_t2(Register dst, SBit s, Condition cond, |
951 uint32_t i, uint32_t imm3, uint32_t imm8); | 971 uint32_t i, uint32_t imm3, uint32_t imm8); |
952 void mov_imm_t3(Register dst, const Operand& src, | 972 void mov_imm_t3(Register dst, const Operand& src, |
953 SBit s, Condition cond); | 973 SBit s, Condition cond); |
954 void mov_reg_t3(Register dst, const Operand& src, | 974 void mov_reg_t3(Register dst, const Operand& src, |
955 SBit s, Condition cond); | 975 SBit s, Condition cond); |
| 976 void mov_thumb(Register dst, const Operand& src, |
| 977 SBit s, Condition cond); |
956 | 978 |
957 void lsl_imm_t2(Register dst, const Operand& src, SBit s, Condition cond); | 979 void lsl_imm_t2(Register dst, const Operand& src, SBit s, Condition cond); |
958 void lsl_reg_t2(Register dst, const Operand& src, SBit s, Condition cond); | 980 void lsl_reg_t2(Register dst, const Operand& src, SBit s, Condition cond); |
| 981 void lsl_thumb(Register dst, const Operand& src, SBit s, Condition cond); |
959 void lsr_imm_t2(Register dst, const Operand& src, SBit s, Condition cond); | 982 void lsr_imm_t2(Register dst, const Operand& src, SBit s, Condition cond); |
960 void lsr_reg_t2(Register dst, const Operand& src, SBit s, Condition cond); | 983 void lsr_reg_t2(Register dst, const Operand& src, SBit s, Condition cond); |
| 984 void lsr_thumb(Register dst, const Operand& src, SBit s, Condition cond); |
961 void asr_imm_t2(Register dst, const Operand& src, SBit s, Condition cond); | 985 void asr_imm_t2(Register dst, const Operand& src, SBit s, Condition cond); |
962 void asr_reg_t2(Register dst, const Operand& src, SBit s, Condition cond); | 986 void asr_reg_t2(Register dst, const Operand& src, SBit s, Condition cond); |
| 987 void asr_thumb(Register dst, const Operand& src, SBit s, Condition cond); |
963 void ror_imm_t2(Register dst, const Operand& src, SBit s, Condition cond); | 988 void ror_imm_t2(Register dst, const Operand& src, SBit s, Condition cond); |
964 void ror_reg_t2(Register dst, const Operand& src, SBit s, Condition cond); | 989 void ror_reg_t2(Register dst, const Operand& src, SBit s, Condition cond); |
| 990 void ror_thumb(Register dst, const Operand& src, SBit s, Condition cond); |
965 | 991 |
966 // Load the position of the label relative to the generated code object | 992 // Load the position of the label relative to the generated code object |
967 // pointer in a register. | 993 // pointer in a register. |
968 void mov_label_offset(Register dst, Label* label); | 994 void mov_label_offset(Register dst, Label* label); |
969 | 995 |
970 // ARMv7 instructions for loading a 32 bit immediate in two instructions. | 996 // ARMv7 instructions for loading a 32 bit immediate in two instructions. |
971 // This may actually emit a different mov instruction, but on an ARMv7 it | 997 // This may actually emit a different mov instruction, but on an ARMv7 it |
972 // is guaranteed to only emit one instruction. | 998 // is guaranteed to only emit one instruction. |
973 void movw(Register reg, uint32_t immediate, Condition cond = al); | 999 void movw(Register reg, uint32_t immediate, Condition cond = al); |
974 // The constant for movt should be in the range 0-0xffff. | 1000 // The constant for movt should be in the range 0-0xffff. |
975 void movt(Register reg, uint32_t immediate, Condition cond = al); | 1001 void movt(Register reg, uint32_t immediate, Condition cond = al); |
| 1002 void movt_thumb(Register reg, uint32_t immediate, Condition cond = al); |
976 | 1003 |
977 void bic(Register dst, Register src1, const Operand& src2, | 1004 void bic(Register dst, Register src1, const Operand& src2, |
978 SBit s = LeaveCC, Condition cond = al); | 1005 SBit s = LeaveCC, Condition cond = al); |
979 void bic_imm_t1(Register dst, Register src1, SBit s, Condition cond, | 1006 void bic_imm_t1(Register dst, Register src1, SBit s, Condition cond, |
980 uint32_t i, uint32_t imm3, uint32_t imm8); | 1007 uint32_t i, uint32_t imm3, uint32_t imm8); |
981 void bic_reg_t2(Register dst, Register src1, const Operand& src2, | 1008 void bic_reg_t2(Register dst, Register src1, const Operand& src2, |
982 SBit s, Condition cond); | 1009 SBit s, Condition cond); |
| 1010 void bic_thumb(Register dst, Register src1, const Operand& src2, |
| 1011 SBit s, Condition cond); |
983 | 1012 |
984 void mvn(Register dst, const Operand& src, | 1013 void mvn(Register dst, const Operand& src, |
985 SBit s = LeaveCC, Condition cond = al); | 1014 SBit s = LeaveCC, Condition cond = al); |
986 void mvn_imm_t1(Register dst, SBit s, Condition cond, | 1015 void mvn_imm_t1(Register dst, SBit s, Condition cond, |
987 uint32_t i, uint32_t imm3, uint32_t imm8); | 1016 uint32_t i, uint32_t imm3, uint32_t imm8); |
988 void mvn_reg_t2(Register dst, const Operand& src, | 1017 void mvn_reg_t2(Register dst, const Operand& src, |
989 SBit s, Condition cond); | 1018 SBit s, Condition cond); |
| 1019 void mvn_thumb(Register dst, const Operand& src, |
| 1020 SBit s, Condition cond); |
990 | 1021 |
991 // Multiply instructions | 1022 // Multiply instructions |
992 | 1023 |
993 void mla(Register dst, Register src1, Register src2, Register srcA, | 1024 void mla(Register dst, Register src1, Register src2, Register srcA, |
994 SBit s = LeaveCC, Condition cond = al); | 1025 SBit s = LeaveCC, Condition cond = al); |
995 | 1026 |
996 void mls(Register dst, Register src1, Register src2, Register srcA, | 1027 void mls(Register dst, Register src1, Register src2, Register srcA, |
997 Condition cond = al); | 1028 Condition cond = al); |
998 | 1029 |
999 void sdiv(Register dst, Register src1, Register src2, | 1030 void sdiv(Register dst, Register src1, Register src2, |
1000 Condition cond = al); | 1031 Condition cond = al); |
1001 | 1032 |
1002 void mul(Register dst, Register src1, Register src2, | 1033 void mul(Register dst, Register src1, Register src2, |
1003 SBit s = LeaveCC, Condition cond = al); | 1034 SBit s = LeaveCC, Condition cond = al); |
1004 void mul_t2(Register dst, Register src1, Register src2, | 1035 void mul_t2(Register dst, Register src1, Register src2, |
1005 SBit s, Condition cond); | 1036 SBit s, Condition cond); |
| 1037 void mul_thumb(Register dst, Register src1, Register src2, |
| 1038 SBit s, Condition cond); |
1006 | 1039 |
1007 void smlal(Register dstL, Register dstH, Register src1, Register src2, | 1040 void smlal(Register dstL, Register dstH, Register src1, Register src2, |
1008 SBit s = LeaveCC, Condition cond = al); | 1041 SBit s = LeaveCC, Condition cond = al); |
1009 | 1042 |
1010 void smull(Register dstL, Register dstH, Register src1, Register src2, | 1043 void smull(Register dstL, Register dstH, Register src1, Register src2, |
1011 SBit s = LeaveCC, Condition cond = al); | 1044 SBit s = LeaveCC, Condition cond = al); |
1012 | 1045 |
1013 void umlal(Register dstL, Register dstH, Register src1, Register src2, | 1046 void umlal(Register dstL, Register dstH, Register src1, Register src2, |
1014 SBit s = LeaveCC, Condition cond = al); | 1047 SBit s = LeaveCC, Condition cond = al); |
1015 | 1048 |
(...skipping 330 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1346 ldr(dst, MemOperand(sp, 4, PostIndex), cond); | 1379 ldr(dst, MemOperand(sp, 4, PostIndex), cond); |
1347 } | 1380 } |
1348 | 1381 |
1349 void pop() { | 1382 void pop() { |
1350 add(sp, sp, Operand(kPointerSize)); | 1383 add(sp, sp, Operand(kPointerSize)); |
1351 } | 1384 } |
1352 | 1385 |
1353 // Jump unconditionally to given label. | 1386 // Jump unconditionally to given label. |
1354 void jmp(Label* L) { b(L, al); } | 1387 void jmp(Label* L) { b(L, al); } |
1355 | 1388 |
| 1389 void it_thumb(Condition cond, int num_instr, bool cond2 = false, |
| 1390 bool cond3 = false, bool cond4 = false); |
| 1391 inline void emit_it(Condition cond); |
| 1392 |
1356 static bool use_immediate_embedded_pointer_loads( | 1393 static bool use_immediate_embedded_pointer_loads( |
1357 const Assembler* assembler) { | 1394 const Assembler* assembler) { |
1358 return CpuFeatures::IsSupported(MOVW_MOVT_IMMEDIATE_LOADS) && | 1395 return CpuFeatures::IsSupported(MOVW_MOVT_IMMEDIATE_LOADS) && |
1359 (assembler == NULL || !assembler->predictable_code_size()); | 1396 (assembler == NULL || !assembler->predictable_code_size()); |
1360 } | 1397 } |
1361 | 1398 |
1362 // Check the code size generated from label to here. | 1399 // Check the code size generated from label to here. |
1363 int SizeOfCodeGeneratedSince(Label* label) { | 1400 int SizeOfCodeGeneratedSince(Label* label) { |
1364 return pc_offset() - label->pos(); | 1401 return pc_offset() - label->pos(); |
1365 } | 1402 } |
(...skipping 400 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1766 public: | 1803 public: |
1767 explicit EnsureSpace(Assembler* assembler) { | 1804 explicit EnsureSpace(Assembler* assembler) { |
1768 assembler->CheckBuffer(); | 1805 assembler->CheckBuffer(); |
1769 } | 1806 } |
1770 }; | 1807 }; |
1771 | 1808 |
1772 | 1809 |
1773 } } // namespace v8::internal | 1810 } } // namespace v8::internal |
1774 | 1811 |
1775 #endif // V8_ARM_ASSEMBLER_ARM_H_ | 1812 #endif // V8_ARM_ASSEMBLER_ARM_H_ |
OLD | NEW |