In my 16bit program GAS is balking at the instruction:
movw %ip, %dx
I find this strange as moving a segment register works fine, for example:
movw %ss, %ax
The full error message is:
Error: bad register name `%ip'
And my version string is:
GNU assembler (GNU Binutils) 2.22
Unfortunately, not every register can be easily accessed. There are some limitations.
As listed in x86 wikibook, GPR section, in x86 there are 8 General-Purpose Registers (GPRs): AX, CX, DX, BX, SP, BP, SI, DI, which can be used in many commands. They are encoded as 3 bits; and there is no space in the instruction encoding to encode Special registers, like EIP (IP), or EFLAGS (FLAGS).
If you scroll wikibook down, there is a section about IP:
Instruction Pointer
The EIP register contains the address of the next instruction to be executed if no branching is done.
EIP can only be read through the stack after a call instruction.
So, it is really illegal to use mov to read IP.
There are some examples of reading ip with call
then pop %ax
sequence here: http://www.programmersheaven.com/mb/x86_asm/267963/267963/how-to-access-ip-register/
Update: About reading of SS register:
There are actually many variant of mov instruction encoding, e.g. in this table we see segment reading
mnemonic op1 op2 po o description, notes
MOV Sreg r/m16 8E r Move
or Control Register writing:
MOV r32 CRn 0F20 r ... Move to Control Registers
but there is still no MOV for IP register.
Update2: in x86_64 there is a reading of EIP with LEA, according to https://stackoverflow.com/a/1047968/196561