[prev in list] [next in list] [prev in thread] [next in thread]
List: gcc-bugs
Subject: Re: Fix preprocessor/7150
From: Jason R Thorpe <thorpej () wasabisystems ! com>
Date: 2002-06-29 19:25:26
[Download RAW message or body]
On Sat, Jun 29, 2002 at 03:35:57PM +0100, Neil Booth wrote:
> Jason, this should fix the segfault that occurred for you
> in cpp_paste_tokens(). It tends to happen if you use
> -imacros or -dM or something that scans code without
> outputting it.
Yes, the segv is gone. But it still doesn't work properly :-)
I've attached some files as an example of the failure.
x86_64-unknown-netbsd-gcc -traditional-cpp -M \
-D_LOCORE -Dx86_64 -D_KERNEL microtime.S
In file included from microtime.S:36:
asm.h:71: unterminated #ifdef
asm.h:64: unterminated #ifndef
asm.h:41: unterminated #ifndef
Also attached is the output of:
x86_64-unknown-netbsd-gcc -traditional-cpp -E \
-D_LOCORE -Dx86_64 -D_KERNEL microtime.S
Look for "SHOULD NOT BE HERE" and "NEITHER SHOULD THIS". Also note that
the _ENTRY() macro (used by ENTRY()) from asm.h does not get expanded.
--
-- Jason R. Thorpe <thorpej@wasabisystems.com>
["tradcpp-bug.shar" (application/x-shar)]
# This is a shell archive. Save it in a file, remove anything before
# this line, and then unpack it by entering "sh file". Note, it may
# create directories; files and directories will be owned by you and
# have default permissions.
#
# This archive contains:
#
# asm.h
# isareg.h
# timerreg.h
# microtime.S
#
echo x - asm.h
sed 's/^X//' >asm.h << 'END-of-asm.h'
X/* $NetBSD: asm.h,v 1.2 2002/06/05 19:17:34 fvdl Exp $ */
X
X/*-
X * Copyright (c) 1990 The Regents of the University of California.
X * All rights reserved.
X *
X * This code is derived from software contributed to Berkeley by
X * William Jolitz.
X *
X * Redistribution and use in source and binary forms, with or without
X * modification, are permitted provided that the following conditions
X * are met:
X * 1. Redistributions of source code must retain the above copyright
X * notice, this list of conditions and the following disclaimer.
X * 2. Redistributions in binary form must reproduce the above copyright
X * notice, this list of conditions and the following disclaimer in the
X * documentation and/or other materials provided with the distribution.
X * 3. All advertising materials mentioning features or use of this software
X * must display the following acknowledgement:
X * This product includes software developed by the University of
X * California, Berkeley and its contributors.
X * 4. Neither the name of the University nor the names of its contributors
X * may be used to endorse or promote products derived from this software
X * without specific prior written permission.
X *
X * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
X * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
X * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
X * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
X * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
X * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
X * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
X * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
X * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
X * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
X * SUCH DAMAGE.
X *
X * @(#)asm.h 5.5 (Berkeley) 5/7/91
X */
X
X#ifndef _X86_64_ASM_H_
X#define _X86_64_ASM_H_
X
X#ifdef PIC
X#define PIC_PLT(x) x@PLT
X#define PIC_GOT(x) x@GOTPCREL(%rip)
X#else
X#define PIC_PLT(x) x
X#define PIC_GOT(x) x
X#endif
X
X# define _C_LABEL(x) x
X#define _ASM_LABEL(x) x
X
X#ifdef __STDC__
X# define __CONCAT(x,y) x ## y
X# define __STRING(x) #x
X#else
X# define __CONCAT(x,y) x/**/y
X# define __STRING(x) "x"
X#endif
X
X/* let kernels and others override entrypoint alignment */
X#ifndef _ALIGN_TEXT
X#define _ALIGN_TEXT .align 4
X#endif
X
X#define _ENTRY(x) \
X .text; _ALIGN_TEXT; .globl x; .type x,@function; x:
X
X#ifdef _KERNEL
X/* XXX Can't use __CONCAT() here, as it would be evaluated incorrectly. */
X#ifdef __STDC__
X#define IDTVEC(name) ALIGN_TEXT; .globl X ## name; X ## name:
X#else
X#define IDTVEC(name) ALIGN_TEXT; .globl X/**/name; X/**/name:
X#endif /* __STDC__ */
X#endif /* _KERNEL */
X
X#ifdef __STDC__
X#define CPUVAR(off) %gs:CPU_INFO_ ## off
X#else
X#define CPUVAR(off) %gs:CPU_INFO_/**/off
X#endif
X
X
X#ifdef GPROF
X# define _PROF_PROLOGUE \
X pushq %rbp; leaq (%rsp),%rbp; call PIC_PLT(__mcount); popq %rbp
X#else
X# define _PROF_PROLOGUE
X#endif
X
X#define ENTRY(y) _ENTRY(_C_LABEL(y)); _PROF_PROLOGUE
X#define NENTRY(y) _ENTRY(_C_LABEL(y))
X#define ASENTRY(y) _ENTRY(_ASM_LABEL(y)); _PROF_PROLOGUE
X
X#define ASMSTR .asciz
X
X#define RCSID(x) .text; .asciz x
X
X#define WEAK_ALIAS(alias,sym) \
X .weak alias; \
X alias = sym; \
X SHOULD NOT BE HERE
X
X/* XXXfvdl do not use stabs here */
X#ifdef __STDC__
X#define WARN_REFERENCES(sym,msg) \
X .stabs msg ## ,30,0,0,0 ; \
X .stabs __STRING(_C_LABEL(sym)) ## ,1,0,0,0
X#else
X#define WARN_REFERENCES(sym,msg) \
X .stabs msg,30,0,0,0 ; \
X .stabs __STRING(sym),1,0,0,0 ; \
X NEITHER SHOULD THIS
X#endif /* __STDC__ */
X
X#endif /* !_X86_64_ASM_H_ */
END-of-asm.h
echo x - isareg.h
sed 's/^X//' >isareg.h << 'END-of-isareg.h'
X/* $NetBSD: isareg.h,v 1.6 1998/03/22 15:44:02 drochner Exp $ */
X
X/*-
X * Copyright (c) 1990 The Regents of the University of California.
X * All rights reserved.
X *
X * This code is derived from software contributed to Berkeley by
X * William Jolitz.
X *
X * Redistribution and use in source and binary forms, with or without
X * modification, are permitted provided that the following conditions
X * are met:
X * 1. Redistributions of source code must retain the above copyright
X * notice, this list of conditions and the following disclaimer.
X * 2. Redistributions in binary form must reproduce the above copyright
X * notice, this list of conditions and the following disclaimer in the
X * documentation and/or other materials provided with the distribution.
X * 3. All advertising materials mentioning features or use of this software
X * must display the following acknowledgement:
X * This product includes software developed by the University of
X * California, Berkeley and its contributors.
X * 4. Neither the name of the University nor the names of its contributors
X * may be used to endorse or promote products derived from this software
X * without specific prior written permission.
X *
X * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
X * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
X * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
X * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
X * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
X * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
X * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
X * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
X * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
X * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
X * SUCH DAMAGE.
X *
X * @(#)isa.h 5.7 (Berkeley) 5/9/91
X */
X
X/*
X * ISA Bus conventions
X */
X
X/*
X * Input / Output Port Assignments
X */
X
X#ifndef IO_ISABEGIN
X#define IO_ISABEGIN 0x000 /* 0x000 - Beginning of I/O Registers */
X
X /* CPU Board */
X#define IO_DMA1 0x000 /* 8237A DMA Controller #1 */
X#define IO_ICU1 0x020 /* 8259A Interrupt Controller #1 */
X#define IO_PMP1 0x026 /* 82347 Power Management Peripheral */
X#define IO_TIMER1 0x040 /* 8253 Timer #1 */
X#define IO_TIMER2 0x048 /* 8253 Timer #2 (EISA only) */
X#define IO_KBD 0x060 /* 8042 Keyboard */
X#define IO_PPI 0x061 /* Programmable Peripheral Interface */
X#define IO_RTC 0x070 /* RTC */
X#define IO_NMI IO_RTC /* NMI Control */
X#define IO_DMAPG 0x080 /* DMA Page Registers */
X#define IO_ICU2 0x0A0 /* 8259A Interrupt Controller #2 */
X#define IO_DMA2 0x0C0 /* 8237A DMA Controller #2 */
X#define IO_NPX 0x0F0 /* Numeric Coprocessor */
X
X /* Cards */
X /* 0x100 - 0x16F Open */
X
X#define IO_WD2 0x170 /* Secondary Fixed Disk Controller */
X#define IO_PMP2 0x178 /* 82347 Power Management Peripheral */
X
X /* 0x17A - 0x1EF Open */
X
X#define IO_WD1 0x1f0 /* Primary Fixed Disk Controller */
X#define IO_GAME 0x200 /* Game Controller */
X
X /* 0x208 - 0x237 Open */
X
X#define IO_BMS2 0x238 /* secondary InPort Bus Mouse */
X#define IO_BMS1 0x23c /* primary InPort Bus Mouse */
X
X /* 0x240 - 0x277 Open */
X
X#define IO_LPT2 0x278 /* Parallel Port #2 */
X
X /* 0x280 - 0x2E7 Open */
X
X#define IO_COM4 0x2e8 /* COM4 i/o address */
X
X /* 0x2F0 - 0x2F7 Open */
X
X#define IO_COM2 0x2f8 /* COM2 i/o address */
X
X /* 0x300 - 0x32F Open */
X
X#define IO_BT0 0x330 /* bustek 742a default addr. */
X#define IO_AHA0 0x330 /* adaptec 1542 default addr. */
X#define IO_UHA0 0x330 /* ultrastore 14f default addr. */
X#define IO_BT1 0x334 /* bustek 742a default addr. */
X#define IO_AHA1 0x334 /* adaptec 1542 default addr. */
X
X /* 0x338 - 0x34F Open */
X
X#define IO_WDS 0x350 /* WD7000 scsi */
X
X /* 0x354 - 0x36F Open */
X
X#define IO_FD2 0x370 /* secondary base i/o address */
X#define IO_LPT1 0x378 /* Parallel Port #1 */
X
X /* 0x380 - 0x3AF Open */
X
X#define IO_MDA 0x3B0 /* Monochome Adapter */
X#define IO_LPT3 0x3BC /* Monochome Adapter Printer Port */
X#define IO_VGA 0x3C0 /* E/VGA Ports */
X#define IO_CGA 0x3D0 /* CGA Ports */
X
X /* 0x3E0 - 0x3E7 Open */
X
X#define IO_COM3 0x3e8 /* COM3 i/o address */
X#define IO_FD1 0x3f0 /* primary base i/o address */
X#define IO_COM1 0x3f8 /* COM1 i/o address */
X
X#define IO_ISAEND 0x3FF /* - 0x3FF End of I/O Registers */
X#endif /* !IO_ISABEGIN */
X
X/*
X * Input / Output Port Sizes - these are from several sources, and tend
X * to be the larger of what was found, ie COM ports can be 4, but some
X * boards do not fully decode the address, thus 8 ports are used.
X */
X
X#ifndef IO_ISASIZES
X#define IO_ISASIZES
X
X#define IO_COMSIZE 8 /* 8250, 16X50 com controllers */
X#define IO_CGASIZE 16 /* CGA controllers */
X#define IO_DMASIZE 16 /* 8237 DMA controllers */
X#define IO_DPGSIZE 32 /* 74LS612 DMA page reisters */
X#define IO_FDCSIZE 8 /* Nec765 floppy controllers */
X#define IO_WDCSIZE 8 /* WD compatible disk controller */
X#define IO_GAMSIZE 16 /* AT compatible game controller */
X#define IO_ICUSIZE 16 /* 8259A interrupt controllers */
X#define IO_KBDSIZE 5 /* 8042 Keyboard controllers */
X#define IO_LPTSIZE 8 /* LPT controllers, some use onl */
X#define IO_MDASIZE 16 /* Monochrome display controller */
X#define IO_RTCSIZE 16 /* CMOS real time clock, NMI con */
X#define IO_TMRSIZE 16 /* 8253 programmable timers */
X#define IO_NPXSIZE 16 /* 80387/80487 NPX registers */
X#define IO_VGASIZE 16 /* VGA controllers */
X#define IO_PMPSIZE 2 /* 82347 Power Management Peripheral */
X#endif /* !IO_ISASIZES */
X
X/*
X * Input / Output Memory Physical Addresses
X */
X
X#ifndef IOM_BEGIN
X#define IOM_BEGIN 0x0a0000 /* Start of I/O Memory "hole" */
X#define IOM_END 0x100000 /* End of I/O Memory "hole" */
X#define IOM_SIZE (IOM_END - IOM_BEGIN)
X#endif /* !IOM_BEGIN */
END-of-isareg.h
echo x - timerreg.h
sed 's/^X//' >timerreg.h << 'END-of-timerreg.h'
X/* $NetBSD: timerreg.h,v 1.4 1994/10/27 04:18:17 cgd Exp $ */
X
X/*-
X * Copyright (c) 1993 The Regents of the University of California.
X * All rights reserved.
X *
X * Redistribution and use in source and binary forms, with or without
X * modification, are permitted provided that the following conditions
X * are met:
X * 1. Redistributions of source code must retain the above copyright
X * notice, this list of conditions and the following disclaimer.
X * 2. Redistributions in binary form must reproduce the above copyright
X * notice, this list of conditions and the following disclaimer in the
X * documentation and/or other materials provided with the distribution.
X * 3. All advertising materials mentioning features or use of this software
X * must display the following acknowledgement:
X * This product includes software developed by the University of
X * California, Berkeley and its contributors.
X * 4. Neither the name of the University nor the names of its contributors
X * may be used to endorse or promote products derived from this software
X * without specific prior written permission.
X *
X * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
X * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
X * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
X * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
X * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
X * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
X * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
X * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
X * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
X * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
X * SUCH DAMAGE.
X */
X
X/*
X * Register definitions for the Intel 8253 Programmable Interval Timer.
X *
X * This chip has three independent 16-bit down counters that can be
X * read on the fly. There are three mode registers and three countdown
X * registers. The countdown registers are addressed directly, via the
X * first three I/O ports. The three mode registers are accessed via
X * the fourth I/O port, with two bits in the mode byte indicating the
X * register. (Why are hardware interfaces always so braindead?).
X *
X * To write a value into the countdown register, the mode register
X * is first programmed with a command indicating the which byte of
X * the two byte register is to be modified. The three possibilities
X * are load msb (TMR_MR_MSB), load lsb (TMR_MR_LSB), or load lsb then
X * msb (TMR_MR_BOTH).
X *
X * To read the current value ("on the fly") from the countdown register,
X * you write a "latch" command into the mode register, then read the stable
X * value from the corresponding I/O port. For example, you write
X * TMR_MR_LATCH into the corresponding mode register. Presumably,
X * after doing this, a write operation to the I/O port would result
X * in undefined behavior (but hopefully not fry the chip).
X * Reading in this manner has no side effects.
X *
X * The outputs of the three timers are connected as follows:
X *
X * timer 0 -> irq 0
X * timer 1 -> dma chan 0 (for dram refresh)
X * timer 2 -> speaker (via keyboard controller)
X *
X * Timer 0 is used to call hardclock.
X * Timer 2 is used to generate console beeps.
X */
X
X/*
X * Frequency of all three count-down timers; (TIMER_FREQ/freq) is the
X * appropriate count to generate a frequency of freq hz.
X */
X#ifndef TIMER_FREQ
X#define TIMER_FREQ 1193182
X#endif
X#define TIMER_DIV(x) ((TIMER_FREQ+(x)/2)/(x))
X
X/*
X * Macros for specifying values to be written into a mode register.
X */
X#define TIMER_CNTR0 (IO_TIMER1 + 0) /* timer 0 counter port */
X#define TIMER_CNTR1 (IO_TIMER1 + 1) /* timer 1 counter port */
X#define TIMER_CNTR2 (IO_TIMER1 + 2) /* timer 2 counter port */
X#define TIMER_MODE (IO_TIMER1 + 3) /* timer mode port */
X#define TIMER_SEL0 0x00 /* select counter 0 */
X#define TIMER_SEL1 0x40 /* select counter 1 */
X#define TIMER_SEL2 0x80 /* select counter 2 */
X#define TIMER_INTTC 0x00 /* mode 0, intr on terminal cnt */
X#define TIMER_ONESHOT 0x02 /* mode 1, one shot */
X#define TIMER_RATEGEN 0x04 /* mode 2, rate generator */
X#define TIMER_SQWAVE 0x06 /* mode 3, square wave */
X#define TIMER_SWSTROBE 0x08 /* mode 4, s/w triggered strobe */
X#define TIMER_HWSTROBE 0x0a /* mode 5, h/w triggered strobe */
X#define TIMER_LATCH 0x00 /* latch counter for reading */
X#define TIMER_LSB 0x10 /* r/w counter LSB */
X#define TIMER_MSB 0x20 /* r/w counter MSB */
X#define TIMER_16BIT 0x30 /* r/w counter 16 bits, LSB first */
X#define TIMER_BCD 0x01 /* count in BCD */
X
END-of-timerreg.h
echo x - microtime.S
sed 's/^X//' >microtime.S << 'END-of-microtime.S'
X/* $NetBSD: microtime.S,v 1.1 2001/06/19 02:06:15 fvdl Exp $ */
X
X/*-
X * Copyright (c) 1993 The Regents of the University of California.
X * All rights reserved.
X *
X * Redistribution and use in source and binary forms, with or without
X * modification, are permitted provided that the following conditions
X * are met:
X * 1. Redistributions of source code must retain the above copyright
X * notice, this list of conditions and the following disclaimer.
X * 2. Redistributions in binary form must reproduce the above copyright
X * notice, this list of conditions and the following disclaimer in the
X * documentation and/or other materials provided with the distribution.
X * 3. All advertising materials mentioning features or use of this software
X * must display the following acknowledgement:
X * This product includes software developed by the University of
X * California, Berkeley and its contributors.
X * 4. Neither the name of the University nor the names of its contributors
X * may be used to endorse or promote products derived from this software
X * without specific prior written permission.
X *
X * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
X * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
X * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
X * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
X * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
X * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
X * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
X * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
X * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
X * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
X * SUCH DAMAGE.
X */
X
X#include "asm.h"
X#include "isareg.h"
X#include "timerreg.h"
X
X#define IRQ_BIT(irq_num) (1 << ((irq_num) & 7))
X#define IRQ_BYTE(irq_num) ((irq_num) >> 3)
X
XENTRY(i8254_microtime)
X # clear registers and do whatever we can up front
X xorl %edx,%edx
X movl $(TIMER_SEL0|TIMER_LATCH),%eax
X
X cli # disable interrupts
X
X # select timer 0 and latch its counter
X outb %al,$TIMER_MODE
X inb $IO_ICU1,%al # as close to timer latch as possible
X movb %al,%ch # %ch is current ICU mask
X
X # Read counter value into [%al %dl], LSB first
X inb $TIMER_CNTR0,%al
X movb %al,%dl # %dl has LSB
X inb $TIMER_CNTR0,%al # %al has MSB
X
X # save state of IIR in ICU, and of ipending, for later perusal
X leaq _C_LABEL(ipending)(%rip),%rsi
X movb IRQ_BYTE(0)(%rsi),%cl # %cl is interrupt pending
X
X # save the current value of _time
X movq _C_LABEL(time)(%rip),%r8 # get time.tv_sec
X movq (_C_LABEL(time)+8)(%rip),%r9 # and time.tv_usec
X
X sti # enable interrupts, we're done
X
X # At this point we've collected all the state we need to
X # compute the time. First figure out if we've got a pending
X # interrupt. If the IRQ0 bit is set in ipending we've taken
X # a clock interrupt without incrementing time, so we bump
X # time.tv_usec by a tick. Otherwise if the ICU shows a pending
X # interrupt for IRQ0 we (or the caller) may have blocked an interrupt
X # with the cli. If the counter is not a very small value (3 as
X # a heuristic), i.e. in pre-interrupt state, we add a tick to
X # time.tv_usec
X
X testb $IRQ_BIT(0),%cl # pending interrupt?
X jnz 1f # yes, increment count
X
X testb $IRQ_BIT(0),%ch # hardware interrupt pending?
X jz 2f # no, continue
X testb %al,%al # MSB zero?
X jnz 1f # no, add a tick
X cmpb $3,%dl # is this small number?
X jbe 2f # yes, continue
X1: addq _C_LABEL(isa_timer_tick)(%rip),%r9 # add a tick
X
X # We've corrected for pending interrupts. Now do a table lookup
X # based on each of the high and low order counter bytes to increment
X # time.tv_usec
X2: leaq _C_LABEL(isa_timer_msb_table)(%rip),%rsi
X movw (%rsi,%rax,2),%ax
X subw (%rsi,%rdx,2),%ax
X addq %rax,%r9 # add msb increment
X
X # Normalize the struct timeval. We know the previous increments
X # will be less than a second, so we'll only need to adjust accordingly
X cmpq $1000000,%r9 # carry in timeval?
X jb 3f
X subq $1000000,%r9 # adjust usec
X incq %r8 # bump sec
X
X3: movq %r8,(%rdi) # tvp->tv_sec = sec
X movq %r9,8(%rdi) # tvp->tv_usec = usec
X
X ret
END-of-microtime.S
exit
["microtime.s" (text/plain)]
# 1 "microtime.S"
# 1 "<built-in>"
# 1 "<command line>"
# 1 "microtime.S"
# 35 "microtime.S"
# 1 "asm.h" 1
# 40 "asm.h"
.text; .align 4; .globl x; .type x,@function; x:
.weak alias; alias = sym; SHOULD NOT BE HERE
.stabs msg,30,0,0,0 ; .stabs "sym",1,0,0,0 ; NEITHER SHOULD THIS
# 37 "microtime.S" 2
# 1 "isareg.h" 1
# 40 "isareg.h"
# 66 "isareg.h"
# 154 "isareg.h"
# 38 "microtime.S" 2
# 1 "timerreg.h" 1
# 35 "timerreg.h"
# 69 "timerreg.h"
# 100 "timerreg.h"
# 39 "microtime.S" 2
;
# clear registers and do whatever we can up front
xorl %edx,%edx
movl $(0x00|0x00),%eax
cli # disable interrupts
# select timer 0 and latch its counter
outb %al,$(0x040 + 3)
inb $0x020,%al # as close to timer latch as possible
movb %al,%ch # %ch is current ICU mask
# Read counter value into [%al %dl], LSB first
inb $(0x040 + 0),%al
movb %al,%dl # %dl has LSB
inb $(0x040 + 0),%al # %al has MSB
# save state of IIR in ICU, and of ipending, for later perusal
leaq ipending(%rip),%rsi
movb ((0) >> 3)(%rsi),%cl # %cl is interrupt pending
# save the current value of _time
movq time(%rip),%r8 # get time.tv_sec
movq (time+8)(%rip),%r9 # and time.tv_usec
sti # enable interrupts, we're done
# At this point we've collected all the state we need to
# compute the time. First figure out if we've got a pending
# interrupt. If the IRQ0 bit is set in ipending we've taken
# a clock interrupt without incrementing time, so we bump
# time.tv_usec by a tick. Otherwise if the ICU shows a pending
# interrupt for IRQ0 we (or the caller) may have blocked an interrupt
# with the cli. If the counter is not a very small value (3 as
# a heuristic), i.e. in pre-interrupt state, we add a tick to
# time.tv_usec
testb $(1 << ((0) & 7)),%cl # pending interrupt?
jnz 1f # yes, increment count
testb $(1 << ((0) & 7)),%ch # hardware interrupt pending?
jz 2f # no, continue
testb %al,%al # MSB zero?
jnz 1f # no, add a tick
cmpb $3,%dl # is this small number?
jbe 2f # yes, continue
1: addq isa_timer_tick(%rip),%r9 # add a tick
# We've corrected for pending interrupts. Now do a table lookup
# based on each of the high and low order counter bytes to increment
# time.tv_usec
2: leaq isa_timer_msb_table(%rip),%rsi
movw (%rsi,%rax,2),%ax
subw (%rsi,%rdx,2),%ax
addq %rax,%r9 # add msb increment
# Normalize the struct timeval. We know the previous increments
# will be less than a second, so we'll only need to adjust accordingly
cmpq $1000000,%r9 # carry in timeval?
jb 3f
subq $1000000,%r9 # adjust usec
incq %r8 # bump sec
3: movq %r8,(%rdi) # tvp->tv_sec = sec
movq %r9,8(%rdi) # tvp->tv_usec = usec
ret
[prev in list] [next in list] [prev in thread] [next in thread]
Configure |
About |
News |
Add a list |
Sponsored by KoreLogic