The conditions for reproducing this bug are a little obtuse, so please bear with me:
1. A structure exists in XDATA memory.
2. That structure has an XDATA pointer as its first member (its a linked list).
3. The placement of the structure in XDATA is such that the pointer member spans a 256B boundary.
4. A function exists that simply takes a pointer to the structure and assigns it to the pointer member (linked list initialisation).
5. That function has external linkage. This is significant, the generated code is different otherwise.
In this specific set of circumstances, the generated code increments the dptr before saving the value of dph. Since dpl is 0xff, the action of incrementing dptr means dph is changed, thus the incorrect value is stored.
Sample code testcase.c attached.
$ sdcc testcase.c
$ sdcc -v
SDCC : mcs51/gbz80/z80/z180/r2k/ds390/pic16/pic14/TININative/ds400/hc08 3.1.0 #7066 (Nov 22 2011) (Mac OS X i386)