Date: Fri, 3 Nov 95 23:51 WET From: uhclem%nemesis@fw.ast.com (Frank Durda IV) To: current@FreeBSD.org Subject: Re: Opcode sequencing Message-ID: <m0tBbW4-000J4YC@nemesis.lonestar.org>
next in thread | raw e-mail | index | archive | help
[3]Bruce Evans <bde@zeta.org.au> writes:
[3]Perhaps the 8254 clock is being accessed too fast. Try adding some delays
[3]before each inb() and outb() in clock.c:getit(). Count to 100 or so to
[3]get at least 1 usec delay.
[4]Uh, I don't think this will work as you expect on a Pentium or a P6. It is
[4]too easy for the parallel integer unit(s) to execute the inb/outbs in one
[4]unit and do the nice delay loop in the other, thus wrecking your timing
[4]delay. On the Pentium and up you must force these types of "timed"
[4]instruction sequences to be done sequentially.
[4]
[4]Execution Time is no longer linear.... :-)
[5]Rod Grimes rgrimes@gndrsh.aac.dev.com writes:
[5]I suggest you go read the book again, IN and OUT instructions are
[5]``serailization'' instuctions. All code between them will have _completed_
[5]execution before the external cycle runs.
Uh, I did. 18-8.5 of Volume 3 of the 1994 Pentium songbook says:
"The I/O instructions are *not* completely serializing; the processor does
*not* wait for these instructions to complete before it prefetches the next
instruction. However, they do have some serializing properties that cause
them to function in a manner that is compatible with processor generations
prior to the Pentium processor."
[Ed: even the 486 and to a lesser extend the 386 had a habit of having
the I/O cycle from an OUT instruction occur AFTER the next instruction
was well-underway. More on this below.]
and Chapter 15.4 "Ordering of I/O" says:
"To optimize performance, the Pentium CPU allows memory reads to be
reordered ahead of buffered writes in most situations. Internally, the
CPU reads (cache hits) can be reordered around buffered writes. Memory
reordering does not occur externally at the pins, read (cache miss) and
writes appear in-order. The Intel486 CPU allows memory reads to be
reordered ahead of buffered writes in certain precisely-defined
circumstances. (See the Intel486TM Microprocessor Hardware Reference
Manual for further details about the operation of the write buffer.)
Using memory-mapped I/O, therefore, creates the possibility that an I/O
read might be performed before the memory write of a previous instruction.
To eliminate this possibility on the Intel486CPU, use an I/O instruction
for the read. ****To eliminate this possibility on the Pentium processor,
insert one of the serializing instructions, such as CPUID, between
operations.****
[Ed: the reverse is also true on a 486 according to the HP 486 Logic Analyzer.
An OUT followed by a memory read obtained data from the wrong location
because the OUT I/O cycle had not occurred by the time the memory read
was performed. (The OUT cycle would have changed memory banks in an
expanded memory system, so the wrong bank was accessed even though the
OUT appeared in the code before the MOV.) The solution was to insert a
JMP $+2 between OUT and MOV opcodes. I don't know if similar or fancier
action is required on the Pentium and this particular case isn't clearly
covered in the Pentium manual.]
When I/O instructions are used instead of memory-mapped I/O, the situation
is different in two respects:
1. Some I/O writes are never buffered. The only I/O writes that the
the Intel486 CPU buffers are those from the OUTS instruction. The
Pentium processor does not buffer any I/O writes. Therefore,
strict ordering of I/O operations is enforced by the processor.
[Ed: Symantics. A plain OUT on a 486 may not be "buffered", but the
I/O WRITE cycle also does not occur during the actual execution clocks of
the OUT instruction. It occurs during or after the next instruction is
performed. So you might call that "deferred". I think they are using
"buffered" to say the I/O cycle does not occur only forced out onto the
bus for some reason, and I agree that is not how it works. The I/O
cycle occurs at a reasonably predictable point. It just isn't in the
confines of the OUT instruction execution period.]
2. The [Pentium] processor synchronizes I/O instruction execution with
*external* bus activity. Refer to Table 15-1.
Table 15-1 [Pentium] I/O Serialization
Processor Holds Awaiting for Completion of...
Execution of...
Current Current Next Pending Current
Instruction Instruction? Instruction Stores? Store?
IN Yes - Yes -
INS Yes - Yes -
REP INS Yes - Yes -
OUT - Yes Yes Yes
OUTS - Yes Yes Yes
REP OUTS - Yes Yes Yes
"
Sorry, I don't know what the difference is between "Current Instruction"
and "Current Instruction?". Perhaps it means an instruction in the
other execution unit (if any) is held while this I/O instruction is
performed.
So much for this bit of trivia.
Frank Durda IV <uhclem@nemesis.lonestar.org>|You want something here
or uhclem%nemesis@fw.ast.com (Fastest Route)|every time?
...letni!rwsys!nemesis!uhclem |
...decvax!fw.ast.com!nemesis!uhclem |
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?m0tBbW4-000J4YC>
