gas/ChangeLog:
* config/tc-i386.c (build_modrm_byte): Dropped the use of
SWAP_SOURCES to encode the vvvv register.
opcodes/ChangeLog:
* i386-opc.h (SWAP_SOURCES): Dropped.
(NO_DEFAULT_MASK): Adjusted the value.
(ADDR_PREFIX_OP_REG): Ditto.
(DISTINCT_DEST): Ditto.
(IMPLICIT_STACK_OP): Ditto.
(VexVVVV_SRC2): New.
* i386-opc.tbl: Dropped SwapSources and replaced its VexVVVV
with Src1VVVV.
* i386-tbl.h: Regenerated.
Use vexvvvv as the switch state, and replace VexVVVV with Src1VVVV.
Src1VVVV means using VEX.vvvv encodes the first source register
operand. The old logic did not check vexvvvv first, which made the
logic here very complicated.
gas/ChangeLog:
* config/tc-i386.c (optimize_encoding): Replaced 1 with Src1VVVV.
(build_modrm_byte): Used vexvvvv to encode the vvvv register.
(s_insn): Replaced 1 with Src1VVVV.
opcodes/ChangeLog:
* i386-opc.h (VexVVVV_DST): Adjusted the value.
(Src1VVVV): New.
* i386-opc.tbl: Replaced part VexVVVV with Src1VVVV.
* i386-tbl.h: Regenerated.
For the case when NDD and NF are both 0 in evex-promoted format,
we will fully support and test it in another patch.
gas/ChangeLog:
* NEWS: Support Intel APX NF.
* config/tc-i386.c (enum i386_error): Add unsupported_nf.
(struct _i386_insn): Add has_nf.
(is_apx_evex_encoding): Ditto.
(build_apx_evex_prefix): Encode the NF bit.
(md_assemble): Handle unsupported_nf.
(parse_insn): Handle Prefix_NF and report bad for illegal combination.
(can_convert_NDD_to_legacy): Replace i.tm.opcode_modifier.nf with i.has_nf.
(match_template): Support D for APX_F insns and check NF support.
* testsuite/gas/i386/x86-64-apx-evex-promoted-bad.d: Add bad test for NF bit.
* testsuite/gas/i386/x86-64-apx-evex-promoted-bad.s: Ditto.
* testsuite/gas/i386/x86-64-apx-inval.l: Ditto.
* testsuite/gas/i386/x86-64-apx-inval.s: Ditto.
* testsuite/gas/i386/x86-64.exp: Add apx nf tests.
* testsuite/gas/i386/x86-64-apx-nf-intel.d: New test.
* testsuite/gas/i386/x86-64-apx-nf.d: Ditto.
* testsuite/gas/i386/x86-64-apx-nf.s: Ditto.
opcodes/ChangeLog:
* i386-dis-evex.h: Add %NF to the instructions that support APX NF and
add new instruction imul, popcnt, tzcnt and lzcnt to EVEX table.
* i386-dis-evex-reg.h: Ditto.
* i386-dis.c (struct instr_info): Add nf.
(struct dis386): Add "NF" for EVEX.NF.
(get_valid_dis386): Set ins->vex.nf and report bad-nf for illegal case.
(print_insn): Handle ins.vex.nf.
(putop): Handle "%NF".
* i386-opc.h (Prefix_NF): New.
* i386-opc.tbl: Added new entries to support full APX NF instructions.
* i386-mnem.h: Regenerated.
* i386-tbl.h: Regenerated.
Already the %bnd<N> registers used numbers beyond 127, and eGPR ones are
all out of reach for "signed char", at least when CHAR_BITS=8. Switch to
"unsigned char", covering appropriately in places where the value
returned for "none" actually matters (in tc_x86_parse_to_dw2regnum()
this is actually achieved by altering how X_op is set).
Some x86 instructions affect the stack pointer implicitly. Add a new
operand constraint to reflect this. This will be useful for SCFI
implmentation to ensure its correctness.
Mark all push, pop, call, ret, enter, leave, INT, iret instructions.
opcodes/
* i386-gen.c: Update opcode_modifiers.
* i386-opc.h: Add a new constraint.
* i386-opc.tbl: Update the affected instructions.
* i386-tbl.h: Regenerated.
Rex2 is currently an operand constraint. For the upcoming SCFI
implementation in GAS, we need to identify operations which implicitly
update the stack pointer. An operand constraint enumerator for implicit
stack op seems more appropriate than an attribute. However, two opcodes
currently necessitate both Rex2 and an implicit stack op marker; this
prompts revisiting the current representations a bit.
Make Rex2 a standalone attribute, so that later a new operand constraint
may be added for IMPLICIT_STACK_OP.
ChangeLog:
* gas/config/tc-i386.c (is_apx_rex2_encoding): Update the check.
* opcodes/i386-gen.c: Add a new BITFIELD for Rex2.
* opcodes/i386-opc.h (REX2_REQUIRED): Remove.
* opcodes/i386-opc.tbl: Remove Rex2 operand constraint.
* opcodes/i386-tbl.h: Regenerated.
Adds two new external authors to etc/update-copyright.py to cover
bfd/ax_tls.m4, and adds gprofng to dirs handled automatically, then
updates copyright messages as follows:
1) Update cgen/utils.scm emitted copyrights.
2) Run "etc/update-copyright.py --this-year" with an extra external
author I haven't committed, 'Kalray SA.', to cover gas testsuite
files (which should have their copyright message removed).
3) Build with --enable-maintainer-mode --enable-cgen-maint=yes.
4) Check out */po/*.pot which we don't update frequently.
This patch adds non-ND, non-NF forms of EVEX promotion insn.
EVEX extension of legacy instructions:
All promoted legacy instructions are placed in EVEX map 4, which is
currently reserved.
EVEX extension of EVEX instructions:
All existing EVEX instructions are extended by APX using the extended
EVEX prefix, so that they can access all 32 GPRs.
EVEX extension of VEX instructions:
Promoting a VEX instruction into the EVEX space does not change the map
id, the opcode, or the operand encoding of the VEX instruction.
Note: The promoted versions of MOVBE will be extended to include the “MOVBE
reg1, reg2”.
gas/ChangeLog:
2023-12-28 Lingling Kong <lingling.kong@intel.com>
H.J. Lu <hongjiu.lu@intel.com>
Lili Cui <lili.cui@intel.com>
Lin Hu <lin1.hu@intel.com>
* config/tc-i386.c (struct _i386_insn): Add has_egpr.
(need_evex_encoding): Adjusted for apx.
(cpu_flags_match): Ditto.
(install_template): Handled APX combines.
(is_apx_evex_encoding): Test apx evex encoding.
(build_apx_evex_prefix): Enabe APX evex prefix.
(md_assemble): Handle apx with evex encoding.
(process_suffix): Handle apx map4 prefix.
(check_register): Assign i.vec_encoding for APX evex instructions.
* testsuite/gas/i386/x86-64-evex.d: Adjust test cases.
* testsuite/gas/i386/x86-64.exp: Adjust x86-64-inval-movbe.
opcodes/ChangeLog:
* i386-dis-evex-len.h: Handle EVEX_LEN_0F38F2, EVEX_LEN_0F38F3.
* i386-dis-evex-prefix.h: Handle PREFIX_EVEX_0F38F2_L_0,
PREFIX_EVEX_0F38F3_L_0, PREFIX_EVEX_MAP4_D8,
PREFIX_EVEX_MAP4_DA, PREFIX_EVEX_MAP4_DB,
PREFIX_EVEX_MAP4_DC, PREFIX_EVEX_MAP4_DD,
PREFIX_EVEX_MAP4_DE, PREFIX_EVEX_MAP4_DF,
PREFIX_EVEX_MAP4_F0, PREFIX_EVEX_MAP4_F1,
PREFIX_EVEX_MAP4_F2, PREFIX_EVEX_MAP4_F8.
* i386-dis-evex-reg.h: Handle REG_EVEX_0F38F3_L_0_P_0.
* i386-dis-evex.h: Add EVEX_MAP4_ for legacy insn
promote to apx to use gpr32
* opcodes/i386-dis-evex-x86-64.h: Handle Add X86_64_EVEX_0F90,
X86_64_EVEX_0F92, X86_64_EVEX_0F93, X86_64_EVEX_0F38F2,
X86_64_EVEX_0F38F3, X86_64_EVEX_0F38F5, X86_64_EVEX_0F38F6,
X86_64_EVEX_0F38F7, X86_64_EVEX_0F3AF0, X86_64_EVEX_0F91.
* i386-dis.c
(struct instr_info): Deleted bool r.
(PREFIX_NP_OR_DATA): New.
(NO_PREFIX): New.
(putop): Ditto.
(X86_64_EVEX_FROM_VEX_TABLE): Diito.
(get_valid_dis386): Decode insn erex in extend evex prefix.
Handle EVEX_MAP4
(print_insn): Handle PREFIX_DATA_AND_NP_ONLY.
(print_register): Handle apx instructions decode.
(OP_E_memory): Diito.
(OP_G): Diito.
(OP_XMM): Diito.
(DistinctDest_Fixup): Diito.
* i386-gen.c (process_i386_opcode_modifier): Add EVEXMAP4.
* i386-opc.h (SPACE_EVEXMAP4): Add legacy insn
promote to evex.
* i386-opc.tbl: Handle some legacy and vex insns don't
support gpr32. And add some legacy insn (map2 / 3) promote
to evex.
Since AVX10.1/256 will also allow 64 bit mask register, we will
remove the restriction for size of the mask register in AVX10.
gas/ChangeLog:
* config/tc-i386.c (VSZ128, VSZ256, VSZ512): New.
(VEX_check_encoding): Remove opcode_modifier check for vsz.
* testsuite/gas/i386/avx10-vsz.l: Remove testcases for mask
registers since they are not needed.
* testsuite/gas/i386/avx10-vsz.s: Ditto.
opcodes/ChangeLog:
* i386-gen.c: Remove Vsz.
* i386-opc.h: Ditto.
* i386-opc.tbl: Remove kvsz.
* i386-tbl.h: Regenerated.
Now that ATTSyntax and ATTMnemonic aren't use in combination anymore,
fold them and IntelSyntax into a single, enum-like attribute. Note that
this shrinks i386_opcode_modifier back to 2 32-bit words (albeit that's
not for long, seeing in-flight additions for APX).
Right now the opcode table has entries with ISA restrictions of the form
FEAT1|FEAT2, the meaning of which depends on context and requires
special treatment in tc-i386.c: Sometimes this means "both features
requires", whereas originally it was intended to solely mean "all of
these features required". Split the field, with the original one
regaining its original meaning. The new field now truly means "any of
these". The combination of both fields is still and &&-type check, i.e.
(all of these) && (any of these). In the opcode table more involved
combinations of features then also need expressing this way: "all"
entities first, follow by "any" entities enclosed in parentheses, e.g.
x64&(AVX|AVX512F). If the "all" part is empty, parentheses may not be
added around the "any" part (unless parsing logic was further relaxed).
Note that this way AVX512VL no longer needs as much special treatment,
and hence templates previously using AVX512F|AVX512VL are switched to
just AVX512VL.
Note further that this requires FMA handling as resulting from
da0784f961 ("x86: fold FMA VEX and EVEX templates") to be slightly
re-done: FMA now becomes more similar to AVX and AVX2.
Now that CpuLM is used solely in cpu_arch_flags and cpu_arch[] while
Cpu64 is solely used in insn templates, they no longer need to be
treated different from other "ordinary" flags; the only "unusual" one
left if CpuNo64. Fold both, leaving just Cpu64.
Recognize "/<number>" suffixes on both -march=+avx10.1 and the
corresponding .arch directive, setting an upper bound on the vector size
that insns may use. Such a restriction can be reset by setting a new base
architecture, by using a suffix-less form, by disabling AVX10, or by
enabling any other VEX/EVEX-based vector extension.
While for most insns we can suppress their use with too wide operands
via registers becoming unavailable (or in Intel syntax memory operand
size specifiers not being recognized), mask register insns have to have
their minimum required vector size specified in a new attribute. (Of
course this new attribute could also be used on other insns.)
Note that .insn continues to be permitted to emit EVEX{512,256} (and
VEX256 ones) encodings regardless of vector size restrictions in place.
Of course these can't be expressed using zmm (or ymm) operands then,
but need using the EVEX.512.* forms (broadcast forms may be usable right
now, but this may go away so shouldn't be relied upon). This is why no
assertions should be added to build_{e,}vex_prefix().
The name we use internally isn't in line with the SDM, and also isn't in
line with CpuVPCLMULQDQ. Add the missing suffix, but of course leave
alone user facing names.
The table constantly growing in two dimensions (number of table entries
times number of ISA extension flags) doesn't scale very well. Use a more
compact representation: Only identifiers which need to combine with
other identifiers retain individual flag bits. All others are combined
into an enum, with a new helper added to transform the table entries
into the original i386_cpu_flags layout. This way the table in the final
binary shrinks by almost a third (the generated source code shrinks by
about half), and isn't likely to grow again in that dimension any time
soon.
While moving the 3DNow! fields, drop the stray inner 'a' from their
names.
The logic can actually be expressed with less code that way, utilizing
that there are common patterns of when which form of masking is
permitted. This then also eliminates the large set of open-codings of
BOTH_MASKING in the opcode table.
All encoding spaces can be used this way; there's a certain risk that
the bits presently reserved could be used for other purposes down the
road, but people using .insn are expected to know what they're doing
anyway. Plus this way there's at least _some_ way to have those bits
set.
For now this will only allow operand-less insns to be encoded this way.
With the SDM long having dropped the NDS/NDD/DDS concept of identifying
encoding variants, we can finally do away with this concept as well. Of
the few consumers of the attribute, only an assertion was still checking
for a particular value, which we don't really need to retain.
When touching lines anyway, modernize other aspects as well. This often
improves similarity to adjacent lines.
The feature isn't universally available on 64-bit CPUs.
Note that in i386-gen.c:isa_dependencies[] I'm only adding it to models
where I'm certain the functionality exists. For Nocona and Core I'm
uncertain in particular.
The attribute really specifies that the sum of register and memory
operands is 4. Express it like that in most places, while using the 2nd
(apart from XOP) CPU feature flags (FMA4) in reversed operand matching
logic.
With the use in build_modrm_byte() gone, part of an assertion there
also becomes meaningless - simplify that at the same time.
With all uses of the opcode modifier field gone, also drop that.
The few XOP insns which used it wrongly didn't have VexVVVV specified.
With that added, the only further missing piece to use more generic code
elsewhere is SwapSources - see e.g. the BMI2 insns for similar operand
patterns.
With the only users gone, drop the #define as well as the special case
code.
This really isn't a "modifier" and rather ought to live next to the base
opcode anyway. Use the bits we presently have available to fit in the
field, renaming it to opcode_space. As an intended side effect this
helps readability at the use sites, by shortening the references quite a
bit.
In generated code arrange for human readable output, by using the
SPACE_* constants there rather than raw numbers. This may aid debugging
down the road.
Register names are (including their nul terminators) on average almost 4
bytes long. Otoh no register name is longer than 7 bytes. Hence even for
32-bit builds using a pointer is only slightly more space efficient than
embedding the strings. A level of indirection can be also avoided by
embedding the names as an array of 8 characters directly in the struct,
and the number of base relocations in PIE builds of gas goes down as
well.
Using full pointers to reference the insn mnemonic strings is not very
efficient. With overall string size presently just slightly over 20k,
even a 16-bit value would suffice. Use "unsigned int" for now, as
there's no good use we could presently make of the otherwise saved 16
bits.
For 64-bit builds this reduces table size by 6.25% (prior to the recent
ISA extension additions it would have been 12.5%), with a similar effect
on cache occupation of table entries accessed. For PIE builds of gas
this also reduces the number of base relocations quite a bit (obviously
independent of bitness).
The newer update-copyright.py fixes file encoding too, removing cr/lf
on binutils/bfdtest2.c and ld/testsuite/ld-cygwin/exe-export.exp, and
embedded cr in binutils/testsuite/binutils-all/ar.exp string match.
While originally indeed used for register size checking only, the
attribute has been used for memory operand size checking as well already
for quite a while, with more such uses recently having been added.
Unlike many other architectures, x86 does not share an opcode table
between assembly and disassembly. Any consumer of libopcodes would only
ever access one of the two. Since gas is the only consumer of the
assembly data, move it there. While doing so mark respective entities
"static" in i386-gen (we may want to do away with i386_regtab_size
altogether).
This also shrinks the number of relocations to be processed for
libopcodes.so by about 30%.
There are just 4 templates using it, which can be easily identified by
other means, as D is set only on a very limited number of FPU templates.
Also move the respective conditional out of the code path taken by all
"reverse match" insns (it probably should have been this way already
before, to avoid the one conditional in the common case).
With this the templates which had FloatR dropped no longer differ from
their AT&T syntax + mnemonic counterparts - the only difference is now
which of the two would be recognized. For this, however, we don't need
two templates - we can simply arrange the condition for setting
Opcode_FloatR accordingly.
Attributes which aren't used together in any single insn template can be
converted from individual booleans to a single enum, as was done for a few
other attributes before. This is more space efficient. Collect together
all attributes which express special operand constraints (and which fit
the criteria for folding).