Index of files in Documentation/fb. If you think something about frame
buffer devices needs an entry here, needs correction or you've written one
please mail me.
- Geert Uytterhoeven
- <Geert.Uytterhoeven@cs.kuleuven.ac.be>
+ Geert Uytterhoeven <geert@linux-m68k.org>
00-INDEX
- this file
The Frame Buffer Device
-----------------------
-Maintained by Geert Uytterhoeven (Geert.Uytterhoeven@cs.kuleuven.ac.be)
+Maintained by Geert Uytterhoeven <geert@linux-m68k.org>
Last revised: November 7, 1998
This is a first start for some documentation about frame buffer device
internals.
-Geert Uytterhoeven <Geert.Uytterhoeven@cs.kuleuven.ac.be>, 21 July 1998
+Geert Uytterhoeven <geert@linux-m68k.org>, 21 July 1998
--------------------------------------------------------------------------------
6. Thanks
- Thanks to Geert Uytterhoeven <Geert.Uytterhoeven@cs.kuleuven.ac.be>
+ Thanks to Geert Uytterhoeven <geert@linux-m68k.org>
for porting the patches from 2.1.4x to 2.1.6x for taking care of
the integration of these patches into m68k, ppc and alpha.
Smart CONFIG_* Dependencies
-Fri 2 Dec 1997
+1 August 1999
Michael Chastain <mec@shout.net>
Werner Almesberger <almesber@lrc.di.epfl.ch>
It now generates these dependencies:
drivers/net/foo.c: \
- include/config/foo_autofrob.h \
- include/config/foo_model_two.h
+ include/config/foo/autofrob.h \
+ include/config/foo/model/two.h
So drivers/net/foo.c depends only on the CONFIG_* lines that
it actually uses.
- A new program, split-include.c, runs at the end of make config (also
- make oldconfig, make menuconfig, and make xconfig). split-include
- reads include/linux/autoconf.h and updates the include/linux/*.h
- directory, writing one file per option. It updates only the files
- that changed.
+ A new program, split-include.c, runs at the beginning of
+ compilation (make bzImage or make zImage). split-include reads
+ include/linux/autoconf.h and updates the include/config/ tree,
+ writing one file per option. It updates only the files for options
+ that have changed.
- mkdep.c also generates much better warning messages for missing
- or unneeded <linux/config.h> lines. In fact, you can get these
- messages without generating dependencies with the new top-level
- target 'make checkconfig'.
+ mkdep.c no longer generates warning messages for missing or unneeded
+ <linux/config.h> lines. The new top-level target 'make checkconfig'
+ checks for these problems.
Flag Dependencies
the compilation flags used to build it. The file foo.o has
its flags stored in .flags.foo.o.
- Suppose the user changes the foo driver from resident to
- modular, 'make' will notice that the foo.o was not compiled
- with -DMODULE and will recompile foo.c.
+ Suppose the user changes the foo driver from resident to modular.
+ 'make' will notice that the current foo.o was not compiled with
+ -DMODULE and will recompile foo.c.
- All .a and .o files made from C source or with 'ld' or 'ar'
- have flag dependencies. .S files do not have flag dependencies.
+ All .o files made from C source have flag dependencies. So do .o
+ files made with ld, and .a files made with ar. However, .o files
+ made from assembly source do not have flag dependencies (nobody
+ needs this yet, but it would be good to fix).
Per-source-file Flags
version of this patch.
Michael Chastain picked it up and continued development. He is
- now the principal author and maintainer. Report bugs to him,
- or to all three people together.
+ now the principal author and maintainer. Please report any bugs
+ to him.
Martin von Loewis wrote flag dependencies, with some modifications
by Michael Chastain.
VERSION = 2
PATCHLEVEL = 3
-SUBLEVEL = 14
+SUBLEVEL = 15
EXTRAVERSION =
ARCH := $(shell uname -m | sed -e s/i.86/i386/ -e s/sun4u/sparc64/ -e s/arm.*/arm/ -e s/sa110/arm/)
DRIVERS := $(DRIVERS) drivers/macintosh/macintosh.a
endif
-ifdef CONFIG_PNP
+ifeq ($(CONFIG_PNP),y)
DRIVERS := $(DRIVERS) drivers/pnp/pnp.a
endif
__writeb(b, addr);
}
-void ___raw_writeb(unsigned short b, unsigned long addr)
+void ___raw_writew(unsigned short b, unsigned long addr)
{
__writew(b, addr);
}
if (count >= 2 && (to & 1) == ((long)from & 1)) {
count -= 2;
do {
- __raw_writeb(*(const u16 *)from, to);
+ __raw_writew(*(const u16 *)from, to);
count -= 2;
to += 2;
from += 2;
/* Handle any initial odd halfword */
if (count >= 2 && (to & 2)) {
- __raw_writeb(c, to);
+ __raw_writew(c, to);
to += 2;
count -= 2;
}
/* The tail is half-word aligned if we have count >= 2 */
if (count >= 2) {
- __raw_writeb(c, to);
+ __raw_writew(c, to);
to += 2;
count -= 2;
}
seg fs
lds si,(bx) ! ds:si is source
- mov cl,#6 ! copy 12 bytes
+ mov cl,#3 ! copy 12 bytes
cld
push di
rep
- movsw
+ movsd
pop di
pop ds
! load the setup-sectors directly after the bootblock.
! Note that 'es' is already set up.
-! Also cx is 0 from rep movsw above.
+! Also cx is 0 from rep movsd above.
load_setup:
xor ah,ah ! reset FDC
#define LOW_BUFFER_START 0x2000
#define LOW_BUFFER_END 0x90000
#define LOW_BUFFER_SIZE ( LOW_BUFFER_END - LOW_BUFFER_START )
-#define HEAP_SIZE 0x2000
+#define HEAP_SIZE 0x3000
static int high_loaded =0;
static uch *high_buffer_start /* = (uch *)(((ulg)&end) + HEAP_SIZE)*/;
xor bh,bh
mov bl,[497] ! get setup sects from boot sector
sub bx,#4 ! LILO loads 4 sectors of setup
- shl bx,#8 ! convert to words
+ shl bx,#7 ! convert to dwords (1sect=2^7 dwords)
mov cx,bx
- shr bx,#3 ! convert to segment
+ shr bx,#2 ! convert to segment
add bx,#SYSSEG
seg cs
mov start_sys_seg,bx
mov ax,#SYSSEG
mov ds,ax
rep
- movsw
+ movsd
mov ax,cs ! aka #SETUPSEG
mov ds,ax
add bx,#0x100
sub di,di
sub si,si
- mov cx,#0x800
+ mov cx,#0x400
rep
- movsw
+ movsd
cmp bx,bp ! we assume start_sys_seg > 0x200,
! so we will perhaps read one page more then
! needed, but never overwrite INITSEG because
#ifdef __SMP__
EXPORT_SYMBOL(cpu_data);
EXPORT_SYMBOL(kernel_flag);
-EXPORT_SYMBOL(smp_invalidate_needed);
EXPORT_SYMBOL(cpu_number_map);
EXPORT_SYMBOL(__cpu_logical_map);
EXPORT_SYMBOL(smp_num_cpus);
#include <linux/malloc.h>
#include <linux/random.h>
#include <linux/smp.h>
-#include <linux/tasks.h>
#include <linux/smp_lock.h>
#include <linux/init.h>
static inline void check_smp_invalidate(int cpu)
{
if (test_bit(cpu, &smp_invalidate_needed)) {
+ struct mm_struct *mm = current->mm;
clear_bit(cpu, &smp_invalidate_needed);
+ if (mm)
+ atomic_set_mask(1 << cpu, &mm->cpu_vm_mask);
local_flush_tlb();
}
}
void free_irq(unsigned int irq, void *dev_id)
{
- struct irqaction * action, **p;
+ struct irqaction **p;
unsigned long flags;
if (irq >= NR_IRQS)
return;
spin_lock_irqsave(&irq_controller_lock,flags);
- for (p = &irq_desc[irq].action; (action = *p) != NULL; p = &action->next) {
- if (action->dev_id != dev_id)
- continue;
+ p = &irq_desc[irq].action;
+ for (;;) {
+ struct irqaction * action = *p;
+ if (action) {
+ struct irqaction **pp = p;
+ p = &action->next;
+ if (action->dev_id != dev_id)
+ continue;
- /* Found it - now remove it from the list of entries */
- *p = action->next;
- if (!irq_desc[irq].action) {
+ /* Found it - now remove it from the list of entries */
+ *pp = action->next;
+ if (irq_desc[irq].action)
+ break;
irq_desc[irq].status |= IRQ_DISABLED;
irq_desc[irq].handler->shutdown(irq);
+ break;
}
+ printk("Trying to free free IRQ%d\n",irq);
+ break;
}
- printk("Trying to free free IRQ%d\n",irq);
spin_unlock_irqrestore(&irq_controller_lock,flags);
}
/*
** linux/amiga/chipram.c
**
-** Modified 03-May-94 by Geert Uytterhoeven
-** (Geert.Uytterhoeven@cs.kuleuven.ac.be)
+** Modified 03-May-94 by Geert Uytterhoeven <geert@linux-m68k.org>
** - 64-bit aligned allocations for full AGA compatibility
*/
* in Chip RAM with the kernel command
* line option `debug=mem'.
*
- * © Copyright 1996 by Geert Uytterhoeven
- * (Geert.Uytterhoeven@cs.kuleuven.ac.be)
+ * © Copyright 1996 by Geert Uytterhoeven <geert@linux-m68k.org>
*
*
* Usage:
* APM screenblank bug fixed Takashi Manabe <manabe@roy.dsl.tutics.tut.jp>
*
* Merge with the abstract console driver by Geert Uytterhoeven
- * <Geert.Uytterhoeven@cs.kuleuven.ac.be>, Jan 1997.
+ * <geert@linux-m68k.org>, Jan 1997.
*
* Original m68k console driver modifications by
*
/*
* Amiga Linux/68k A2065 Ethernet Driver
*
- * (C) Copyright 1995 by Geert Uytterhoeven
- * (Geert.Uytterhoeven@cs.kuleuven.ac.be)
+ * (C) Copyright 1995 by Geert Uytterhoeven <geert@linux-m68k.org>
*
* Fixes and tips by:
* - Janos Farkas (CHEXUM@sparta.banki.hu)
/*
* Amiga Linux/68k A2065 Ethernet Driver
*
- * (C) Copyright 1995 by Geert Uytterhoeven
- * (Geert.Uytterhoeven@cs.kuleuven.ac.be)
+ * (C) Copyright 1995 by Geert Uytterhoeven <geert@linux-m68k.org>
*
* ---------------------------------------------------------------------------
*
/*
* Amiga Linux/m68k Ariadne Ethernet Driver
*
- * © Copyright 1995 by Geert Uytterhoeven
- * (Geert.Uytterhoeven@cs.kuleuven.ac.be)
+ * © Copyright 1995 by Geert Uytterhoeven (geert@linux-m68k.org)
* Peter De Schrijver
* (Peter.DeSchrijver@linux.cc.kuleuven.ac.be)
*
/*
* Amiga Linux/m68k Ariadne Ethernet Driver
*
- * © Copyright 1995 by Geert Uytterhoeven
- * (Geert.Uytterhoeven@cs.kuleuven.ac.be)
+ * © Copyright 1995 by Geert Uytterhoeven (geert@linux-m68k.org)
* Peter De Schrijver
* (Peter.DeSchrijver@linux.cc.kuleuven.ac.be)
*
Fix bug in pci_probe() for 64 bit systems reported
by <belliott@accessone.com>.
0.533 9-Jan-98 Fix more 64 bit bugs reported by <jal@cs.brown.edu>.
- 0.534 24-Jan-98 Fix last (?) endian bug from
- <Geert.Uytterhoeven@cs.kuleuven.ac.be>
+ 0.534 24-Jan-98 Fix last (?) endian bug from <geert@linux-m68k.org>
0.535 21-Feb-98 Fix Ethernet Address PROM reset bug for DC21040.
0.536 21-Mar-98 Change pci_probe() to use the pci_dev structure.
**Incompatible with 2.0.x from here.**
/* also some code & lots of fixes by Timo Rossi (trossi@cc.jyu.fi) */
/* The code is mostly based on the linux/68k Ariadne driver */
-/* copyrighted by Geert Uytterhoeven (Geert.Uytterhoeven@cs.kuleuven.ac.be) */
+/* copyrighted by Geert Uytterhoeven (geert@linux-m68k.org) */
/* and Peter De Schrijver (Peter.DeSchrijver@linux.cc.kuleuven.ac.be) */
/* This file is subject to the terms and conditions of the GNU General */
if (dev->descriptor.bNumConfigurations != 1)
return -1;
- interface = &dev->config[0].altsetting[0].interface[0];
+ interface = &dev->config[0].interface[0].altsetting[0];
/* Is it a CPiA? */
if (dev->descriptor.idVendor != 0x0553)
if (dev->descriptor.bNumConfigurations < 1)
return -1;
- interface = &dev->config[0].altsetting[0].interface[0];
+ interface = &dev->config[0].interface[0].altsetting[0];
endpoint = &interface->endpoint[0];
if(interface->bInterfaceClass != 3
protocol = US_PR_CB;
subclass = US_SC_8070; /* an assumption */
} else if (dev->descriptor.bDeviceClass != 0 ||
- dev->config->altsetting->interface->bInterfaceClass != 8 ||
- dev->config->altsetting->interface->bInterfaceSubClass < US_SC_MIN ||
- dev->config->altsetting->interface->bInterfaceSubClass > US_SC_MAX) {
+ dev->config->interface->altsetting->bInterfaceClass != 8 ||
+ dev->config->interface->altsetting->bInterfaceSubClass < US_SC_MIN ||
+ dev->config->interface->altsetting->bInterfaceSubClass > US_SC_MAX) {
return -1;
}
memset(ss, 0, sizeof(struct us_data));
}
- interface = dev->config->altsetting->interface;
+ interface = dev->config->interface->altsetting;
ss->filter = filter;
ss->fdata = fdata;
ss->flags = flags;
s3trio_init(dp);
address = 0xc6000000;
s3trio_base = ioremap(address,64*1024*1024);
- fb_fix.smem_start = (char *)address;
+ fb_fix.smem_start = address;
fb_fix.type = FB_TYPE_PACKED_PIXELS;
fb_fix.type_aux = 0;
fb_fix.accel = FB_ACCEL_S3_TRIO64;
- fb_fix.mmio_start = (char *)address+0x1000000;
+ fb_fix.mmio_start = address+0x1000000;
fb_fix.mmio_len = 0x1000000;
fb_fix.xpanstep = 1;
else
display = &global_disp;
- fix->smem_start = (char *)current_par.screen_base_p;
+ fix->smem_start = current_par.screen_base_p;
fix->smem_len = current_par.screen_size;
fix->type = display->type;
fix->type_aux = display->type_aux;
{
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id, amifb_name);
- fix->smem_start = (char *)videomemory_phys;
+ fix->smem_start = videomemory_phys;
fix->smem_len = videomemorysize;
#ifdef FBCON_HAS_MFB
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id, atyfb_name);
- fix->smem_start = (char *)info->frame_buffer_phys;
+ fix->smem_start = info->frame_buffer_phys;
fix->smem_len = (u32)info->total_vram;
#ifdef __LITTLE_ENDIAN
* Reg Block 1 (multimedia extensions) is at ati_regbase_phys-0x400
*/
if (Gx == GX_CHIP_ID || Gx == CX_CHIP_ID) {
- fix->mmio_start = (char *)info->ati_regbase_phys;
+ fix->mmio_start = info->ati_regbase_phys;
fix->mmio_len = 0x400;
fix->accel = FB_ACCEL_ATI_MACH64GX;
} else if (Gx == CT_CHIP_ID || Gx == ET_CHIP_ID) {
- fix->mmio_start = (char *)info->ati_regbase_phys;
+ fix->mmio_start = info->ati_regbase_phys;
fix->mmio_len = 0x400;
fix->accel = FB_ACCEL_ATI_MACH64CT;
} else if (Gx == VT_CHIP_ID || Gx == VU_CHIP_ID || Gx == VV_CHIP_ID) {
- fix->mmio_start = (char *)(info->ati_regbase_phys-0x400);
+ fix->mmio_start = info->ati_regbase_phys-0x400);
fix->mmio_len = 0x800;
fix->accel = FB_ACCEL_ATI_MACH64VT;
} else {
- fix->mmio_start = (char *)(info->ati_regbase_phys-0x400);
+ fix->mmio_start = info->ati_regbase_phys-0x400);
fix->mmio_len = 0x800;
fix->accel = FB_ACCEL_ATI_MACH64GT;
}
int i;
strcpy(p->fix.id, "C&T 65550");
- p->fix.smem_start = (char *) p->frame_buffer_phys;
+ p->fix.smem_start = p->frame_buffer_phys;
// FIXME: Assumes 1MB frame buffer, but 65550 supports 1MB or 2MB.
// * "3500" PowerBook G3 (the original PB G3) has 2MB.
*
*/
-#define CLGEN_VERSION "1.9.4.1"
+#define CLGEN_VERSION "1.9.4.2"
#include <linux/module.h>
#include <linux/kernel.h>
if(!(expr)) { \
printk( "Assertion failed! %s,%s,%s,line=%d\n",\
#expr,__FILE__,__FUNCTION__,__LINE__); \
- *(int*)0 = 0;\
}
#else
#define assert(expr)
switch (_par->var.bits_per_pixel) {
case 1:
case 8:
- fix->smem_start = (char *) _info->fbmem_phys;
+ fix->smem_start = _info->fbmem_phys;
break;
case 16:
- fix->smem_start = (char *) _info->fbmem_phys + 1 * MB_;
+ fix->smem_start = _info->fbmem_phys + 1 * MB_;
break;
case 24:
case 32:
- fix->smem_start = (char *) _info->fbmem_phys + 2 * MB_;
+ fix->smem_start = _info->fbmem_phys + 2 * MB_;
break;
}
} else {
- fix->smem_start = (char *) _info->fbmem_phys;
+ fix->smem_start = _info->fbmem_phys;
}
/* monochrome: only 1 memory plane */
fix->line_length = _par->line_length;
/* FIXME: map region at 0xB8000 if available, fill in here */
- fix->mmio_start = (char *) NULL;
+ fix->mmio_start = 0;
fix->mmio_len = 0;
fix->accel = FB_ACCEL_NONE;
if (_par->var.yoffset > _par->var.yres_virtual - _par->var.yres)
_par->var.yoffset = _par->var.yres_virtual - _par->var.yres - 1;
- switch (var->bits_per_pixel) {
+ switch (_par->var.bits_per_pixel) {
case 1:
_par->line_length = _par->var.xres_virtual / 8;
_par->visual = FB_VISUAL_MONO10;
break;
default:
- assert (0);
+ DPRINTK("Unsupported bpp size: %d\n", _par->var.bits_per_pixel);
+ assert (FALSE);
/* should never occur */
break;
}
bestclock (freq, &_par->freq, &_par->nom, &_par->den, &_par->div,
maxclock);
- _par->mclk = clgen_get_mclk (freq, var->bits_per_pixel, &_par->divMCLK);
+ _par->mclk = clgen_get_mclk (freq, _par->var.bits_per_pixel, &_par->divMCLK);
xres = _par->var.xres;
hfront = _par->var.right_margin;
clgen_pci_probe_list[i].device, NULL);
if (pdev)
- *btype = clgen_pci_probe_list[i].btype;
+ *btype = clgen_pci_probe_list[i - 1].btype;
DPRINTK ("EXIT, returning %p\n", pdev);
return pdev;
*key2_o = zorro_find (clgen_zorro_probe_list[i].key2, 0, 0);
else
*key2_o = 0;
- *btype = clgen_zorro_probe_list[i].btype;
+ *btype = clgen_zorro_probe_list[i - 1].btype;
printk (KERN_INFO "clgen: %s board detected; ",
clgen_board_info[*btype].name);
break;
default:
/* should never occur */
- assert (0);
+ assert (FALSE);
break;
}
{
memset(fix, 0, sizeof(*fix));
strcpy(fix->id, "control");
- fix->mmio_start = (char *)p->control_regs_phys;
+ fix->mmio_start = p->control_regs_phys;
fix->mmio_len = sizeof(struct control_regs);
fix->type = FB_TYPE_PACKED_PIXELS;
fix->xpanstep = 0;
*/
- fix->smem_start = (void *)(p->frame_buffer_phys
+ fix->smem_start = (p->frame_buffer_phys
+ control_reg_init[par->vmode-1]->offset[par->cmode]);
fix->smem_len = p->total_vram - control_reg_init[par->vmode-1]->offset[par->cmode];
fix->visual = (par->cmode == CMODE_8) ?
else
display = &global_disp;
- fix->smem_start = (char *)current_par.screen_base_p;
+ fix->smem_start = current_par.screen_base_p;
fix->smem_len = current_par.screen_size;
- fix->mmio_start = (char *)current_par.regs_base_p;
+ fix->mmio_start = current_par.regs_base_p;
fix->mmio_len = 0x000c0000;
fix->type = display->type;
fix->type_aux = display->type_aux;
DPRINTK("ENTER\n");
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id, cyberfb_name);
- fix->smem_start = (char*) CyberMem_phys;
+ fix->smem_start = CyberMem_phys;
fix->smem_len = CyberSize;
- fix->mmio_start = (char*) CyberRegs_phys;
+ fix->mmio_start = CyberRegs_phys;
fix->mmio_len = 0x10000;
fix->type = FB_TYPE_PACKED_PIXELS;
{
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id,"Apollo Mono");
- fix->smem_start=(char*)(FRAME_BUFFER_START+IO_BASE);
+ fix->smem_start=FRAME_BUFFER_START+IO_BASE;
fix->smem_len=FRAME_BUFFER_LEN;
fix->type=FB_TYPE_PACKED_PIXELS;
fix->type_aux=0;
fb->fb_get_fix(&fix, PROC_CONSOLE(info), info);
/* frame buffer memory */
- start = (unsigned long)fix.smem_start;
+ start = fix.smem_start;
len = (start & ~PAGE_MASK)+fix.smem_len;
start &= PAGE_MASK;
len = (len+~PAGE_MASK) & PAGE_MASK;
fb->fb_get_var(&var, PROC_CONSOLE(info), info);
if (var.accel_flags)
return -EINVAL;
- start = (unsigned long)fix.mmio_start;
+ start = fix.mmio_start;
len = (start & ~PAGE_MASK)+fix.mmio_len;
start &= PAGE_MASK;
len = (len+~PAGE_MASK) & PAGE_MASK;
#else
#warning What do we have to do here??
#endif
- if (remap_page_range(vma->vm_start, vma->vm_offset,
+ if (io_remap_page_range(vma->vm_start, vma->vm_offset,
vma->vm_end - vma->vm_start, vma->vm_page_prot))
return -EAGAIN;
return 0;
fb_var = fb_var_modes[fm2fb_mode];
strcpy(fb_fix.id, is_fm ? "FrameMaster II" : "Rainbow II");
- fb_fix.smem_start = (char *)fm2fb_mem_phys;
+ fb_fix.smem_start = fm2fb_mem_phys;
fb_fix.smem_len = FRAMEMASTER_REG;
fb_fix.type = FB_TYPE_PACKED_PIXELS;
fb_fix.type_aux = 0;
fb_fix.visual = FB_VISUAL_TRUECOLOR;
fb_fix.line_length = 768<<2;
- fb_fix.mmio_start = (char *)fm2fb_reg_phys;
+ fb_fix.mmio_start = fm2fb_reg_phys;
fb_fix.mmio_len = 8;
fb_fix.accel = FB_ACCEL_NONE;
fb_var.yres = yres;
fb_fix.line_length = (xres / 8) * fb_var.bits_per_pixel;
- fb_fix.smem_start = (char *)0x40000000; /* physical address */
+ fb_fix.smem_start = 0x40000000; /* physical address */
/* get size of video memory; this is special for the JAZZ hardware */
mem = (r4030_read_reg32(JAZZ_R4030_CONFIG) >> 8) & 3;
fb_fix.smem_len = (1 << (mem*2)) * 512 * 1024;
fb_fix.xpanstep = 0;
fb_fix.ypanstep = 1;
fb_fix.ywrapstep = 0;
- fb_fix.mmio_start = NULL;
+ fb_fix.mmio_start = 0;
fb_fix.mmio_len = 0;
fb_fix.accel = FB_ACCEL_NONE;
/*
* X works, but screen wraps ...
*/
- fix->smem_start=(char *)fb_start;
+ fix->smem_start=fb_start;
fix->smem_len=fb_size;
fix->type = FB_TYPE_PACKED_PIXELS;
fix->visual = FB_VISUAL_PSEUDOCOLOR;
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id, igafb_name);
- fix->smem_start = (char *)fb->frame_buffer;
+ fix->smem_start = fb->frame_buffer;
fix->smem_len = fb->total_vram;
fix->xpanstep = 0;
fix->ypanstep = 0;
}
sprintf(p->fix.id, "IMS TT (%s)", p->ramdac == IBM ? "IBM" : "TVP");
- p->fix.smem_start = (__u8 *)p->frame_buffer_phys;
+ p->fix.smem_start = p->frame_buffer_phys;
p->fix.smem_len = p->total_vram;
- p->fix.mmio_start = (__u8 *)p->dc_regs_phys;
+ p->fix.mmio_start = p->dc_regs_phys;
p->fix.mmio_len = 0x1000;
p->fix.accel = FB_ACCEL_IMS_TWINTURBO;
p->fix.type = FB_TYPE_PACKED_PIXELS;
/*
* fbmem.c accepts non page aligned mappings now!
*/
- fix->smem_start=(char *)mac_videobase;
+ fix->smem_start=mac_videobase;
fix->smem_len=mac_videosize;
fix->type = FB_TYPE_PACKED_PIXELS;
if (mac_depth == 1)
/* --------------------------------------------------------------------- */
static struct fb_var_screeninfo vesafb_defined __initdata = {
- 0,0,0,0, /* W,H, W, H (virtual) load xres,xres_virtual*/
+ 640,480,640,480,/* W,H, W, H (virtual) load xres,xres_virtual*/
0,0, /* virtual -> visible no offset */
8, /* depth -> load bits_per_pixel */
0, /* greyscale ? */
FB_ACTIVATE_NOW,
-1,-1,
FB_ACCELF_TEXT, /* accel flags */
- 0L,0L,0L,0L,0L,
- 0L,0L,0, /* No sync info */
+ 39721L,48L,16L,33L,10L,
+ 96L,2L,~0, /* No sync info */
FB_VMODE_NONINTERLACED,
{0,0,0,0,0,0}
};
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id,"MATROX");
- fix->smem_start = (void*)ACCESS_FBINFO(video.base) + ACCESS_FBINFO(curr.ydstorg.bytes);
+ fix->smem_start = ACCESS_FBINFO(video.base) + ACCESS_FBINFO(curr.ydstorg.bytes);
fix->smem_len = ACCESS_FBINFO(video.len_usable) - ACCESS_FBINFO(curr.ydstorg.bytes);
fix->type = p->type;
fix->type_aux = p->type_aux;
fix->ypanstep = 1;
fix->ywrapstep = 0;
fix->line_length = p->line_length;
- fix->mmio_start = (void*)ACCESS_FBINFO(mmio.base);
+ fix->mmio_start = ACCESS_FBINFO(mmio.base);
fix->mmio_len = ACCESS_FBINFO(mmio.len);
fix->accel = ACCESS_FBINFO(devflags.accelerator);
return 0;
else if (!strncmp(this_opt, "vesa:", 5))
vesa = simple_strtoul(this_opt+5, NULL, 0);
else if (!strncmp(this_opt, "font:", 5))
- strcpy(fontname, this_opt+5);
+ strncpy(fontname, this_opt+5, sizeof(fontname)-1);
else if (!strncmp(this_opt, "maxclk:", 7))
maxclk = simple_strtoul(this_opt+7, NULL, 0);
else if (!strncmp(this_opt, "fh:", 3))
else if (!strncmp(this_opt, "mem:", 4))
mem = simple_strtoul(this_opt+4, NULL, 0);
else if (!strncmp(this_opt, "mode:", 5))
- strcpy(videomode, this_opt+5);
+ strncpy(videomode, this_opt+5, sizeof(videomode)-1);
#ifdef CONFIG_FB_OF
else if (!strncmp(this_opt, "vmode:", 6)) {
unsigned int vmode = simple_strtoul(this_opt+6, NULL, 0);
else if (!strcmp(this_opt, "grayscale"))
grayscale = value;
else {
- printk(KERN_ERR "matroxfb: unknown parameter %s%s\n", value?"":"no", this_opt);
+ strncpy(videomode, this_opt, sizeof(videomode)-1);
}
}
}
if (depth == -1)
depth = RSDepth(RSptr->info);
}
-#if 0
- if (sync == -1) {
- sync = 0;
- if (yres < 400)
- sync |= FB_SYNC_HOR_HIGH_ACT;
- else if (yres < 480)
- sync |= FB_SYNC_VERT_HIGH_ACT;
- }
-#endif
if ((depth == RSText8) && (!*ACCESS_FBINFO(fbcon.fontname))) {
strcpy(ACCESS_FBINFO(fbcon.fontname), "VGA8x8");
}
ACCESS_FBINFO(fbcon.flags) = FBINFO_FLAG_DEFAULT;
ACCESS_FBINFO(video.len_usable) &= PAGE_MASK;
-#if 0
- fb_find_mode(&vesafb_defined, &ACCESS_FBINFO(fbcon), videomode[0]?videomode:NULL,
- NULL, 0, NULL, vesafb_defined.bits_per_pixel);
+#ifndef MODULE
+ /* mode database is marked __init ... */
+ {
+ /* it cannot be static const struct due to __initdata
+ marker */
+ static struct fb_videomode defaultmode __initdata = {
+ /* 640x480 @ 60Hz, 31.5 kHz */
+ NULL, 60, 640, 480, 39721, 40, 24, 32, 11, 96, 2,
+ 0, FB_VMODE_NONINTERLACED
+ };
+
+ fb_find_mode(&vesafb_defined, &ACCESS_FBINFO(fbcon), videomode[0]?videomode:NULL,
+ NULL, 0, &defaultmode, vesafb_defined.bits_per_pixel);
+ }
#endif
+
/* mode modifiers */
- if (sync != -1)
- vesafb_defined.sync = sync;
if (hslen)
vesafb_defined.hsync_len = hslen;
if (vslen)
vesafb_defined.xres = xres;
if (yres)
vesafb_defined.yres = yres;
+ if (sync != -1)
+ vesafb_defined.sync = sync;
+ else if (vesafb_defined.sync == ~0) {
+ vesafb_defined.sync = 0;
+ if (yres < 400)
+ vesafb_defined.sync |= FB_SYNC_HOR_HIGH_ACT;
+ else if (yres < 480)
+ vesafb_defined.sync |= FB_SYNC_VERT_HIGH_ACT;
+ }
+
/* fv, fh, maxclk limits was specified */
{
unsigned int tmp;
var->yres = var->yres_virtual = height;
fix->line_length = pitch;
- fix->smem_start = (char *)address;
+ fix->smem_start = address;
fix->smem_len = pitch * height;
fix->type = FB_TYPE_PACKED_PIXELS;
fix->type_aux = 0;
{
memset(fix, 0, sizeof(*fix));
strcpy(fix->id, "platinum");
- fix->smem_start = (void *) (info->frame_buffer_phys + 0x1000);
+ fix->smem_start = (info->frame_buffer_phys + 0x1000);
fix->smem_len = (u32) info->total_vram - 0x1000;
- fix->mmio_start = (char *) (info->platinum_regs_phys);
+ fix->mmio_start = (info->platinum_regs_phys);
fix->mmio_len = 0x1000;
fix->type = FB_TYPE_PACKED_PIXELS;
fix->type_aux = 0;
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id,"Q40");
- fix->smem_start=(char*)q40_screen_addr;
+ fix->smem_start=q40_screen_addr;
fix->smem_len=1024*1024;
fix->type=FB_TYPE_PACKED_PIXELS;
fix->type_aux=0;
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id, retz3fb_name);
- fix->smem_start = (char *)(zinfo->physfbmem);
+ fix->smem_start = zinfo->physfbmem;
fix->smem_len = zinfo->fbsize;
- fix->mmio_start = (char *)(zinfo->physregs);
+ fix->mmio_start = zinfo->physregs;
fix->mmio_len = 0x00c00000;
fix->type = FB_TYPE_PACKED_PIXELS;
{
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id, sgivwfb_name);
- fix->smem_start = (char *) sgivwfb_mem_phys;
+ fix->smem_start = sgivwfb_mem_phys;
fix->smem_len = sgivwfb_mem_size;
fix->type = FB_TYPE_PACKED_PIXELS;
fix->type_aux = 0;
fix->xpanstep = 0;
fix->ypanstep = ypan;
fix->line_length = get_line_length(var->xres_virtual, var->bits_per_pixel);
- fix->mmio_start = (char *) DBE_REG_PHYS;
+ fix->mmio_start = DBE_REG_PHYS;
fix->mmio_len = DBE_REG_SIZE;
}
fix->visual = FB_VISUAL_TRUECOLOR;
fix->line_length = par->xres * (par->bits_per_pixel >> 3);
- fix->smem_start = ioremap(fb_info.tga_fb_base);
+ fix->smem_start = fb_info.tga_fb_base;
fix->smem_len = fix->line_length * par->yres;
- fix->mmio_start = ioremap(fb_info.tga_regs_base);
+ fix->mmio_start = fb_info.tga_regs_base;
fix->mmio_len = 0x1000; /* Is this sufficient? */
fix->xpanstep = fix->ypanstep = fix->ywrapstep = 0;
fix->accel = FB_ACCEL_DEC_TGA;
struct fb_fix_screeninfo *fix,
struct fb_info_valkyrie *p)
{
- fix->smem_start = (void *)(p->frame_buffer_phys + 0x1000);
+ fix->smem_start = p->frame_buffer_phys + 0x1000;
#if 1
fix->smem_len = valkyrie_vram_reqd(par->vmode, par->cmode);
#else
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id,"VESA VGA");
- fix->smem_start=(char *) video_base;
+ fix->smem_start=video_base;
fix->smem_len=video_size;
fix->type = video_type;
fix->visual = video_visual;
{
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id, vfb_name);
- fix->smem_start = (char *)videomemory;
+ fix->smem_start = videomemory;
fix->smem_len = videomemorysize;
fix->type = FB_TYPE_PACKED_PIXELS;
fix->type_aux = 0;
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id,"VGA16 VGA");
- fix->smem_start = (char *) 0xa0000;
+ fix->smem_start = 0xa0000;
fix->smem_len = 65536;
fix->type = FB_TYPE_VGA_PLANES;
fix->visual = FB_VISUAL_PSEUDOCOLOR;
memset(fix, 0, sizeof(struct fb_fix_screeninfo));
strcpy(fix->id, virgefb_name);
if (cv3d_on_zorro2) {
- fix->smem_start = (char*) CyberMem_phys;
+ fix->smem_start = CyberMem_phys;
} else {
switch (par->bpp) {
case 8:
- fix->smem_start = (char*) (CyberMem_phys + CYBMEM_OFFSET_8);
+ fix->smem_start = (CyberMem_phys + CYBMEM_OFFSET_8);
break;
case 16:
- fix->smem_start = (char*) (CyberMem_phys + CYBMEM_OFFSET_16);
+ fix->smem_start = (CyberMem_phys + CYBMEM_OFFSET_16);
break;
}
}
fix->smem_len = CyberSize;
- fix->mmio_start = (char*) CyberRegs_phys;
+ fix->mmio_start = CyberRegs_phys;
fix->mmio_len = 0x10000; /* TODO: verify this for the CV64/3D */
fix->type = FB_TYPE_PACKED_PIXELS;
}
if (metadata) {
result = getblk (inode->i_dev, tmp, blocksize);
+ memset(result->b_data, 0, blocksize);
+ mark_buffer_uptodate(result, 1);
+ mark_buffer_dirty(result, 1);
if (*p) {
ext2_free_blocks (inode, tmp, 1);
- brelse (result);
+ bforget (result);
goto repeat;
}
- memset(result->b_data, 0, blocksize);
- mark_buffer_uptodate(result, 1);
- mark_buffer_dirty(result, 1);
} else {
if (*p) {
/*
* Nobody is allowed to change block allocation
* state from under us:
*/
+ ext2_error (inode->i_sb, "block_getblk",
+ "data block filled under us");
BUG();
ext2_free_blocks (inode, tmp, 1);
goto repeat;
goto out;
if (metadata) {
result = getblk (bh->b_dev, tmp, blocksize);
+ memset(result->b_data, 0, inode->i_sb->s_blocksize);
+ mark_buffer_uptodate(result, 1);
+ mark_buffer_dirty(result, 1);
if (*p) {
ext2_free_blocks (inode, tmp, 1);
- brelse (result);
+ bforget (result);
goto repeat;
}
- memset(result->b_data, 0, inode->i_sb->s_blocksize);
- mark_buffer_uptodate(result, 1);
- mark_buffer_dirty(result, 1);
} else {
+ if (*p) {
+ /*
+ * Nobody is allowed to change block allocation
+ * state from under us:
+ */
+ ext2_error (inode->i_sb, "block_getblk",
+ "data block filled under us");
+ BUG();
+ ext2_free_blocks (inode, tmp, 1);
+ goto repeat;
+ }
*phys = tmp;
*new = 1;
}
- if (*p) {
- ext2_free_blocks (inode, tmp, 1);
- brelse (result);
- goto repeat;
- }
*p = le32_to_cpu(tmp);
mark_buffer_dirty(bh, 1);
if (IS_SYNC(inode) || inode->u.ext2_i.i_osync) {
* FIXME! This could use version numbering or similar to
* avoid unnecessary cache lookups.
*/
- result = cached_lookup(parent, name, flags);
+ result = d_lookup(parent, name);
if (!result) {
struct dentry * dentry = d_alloc(parent, name);
result = ERR_PTR(-ENOMEM);
else
result = dentry;
}
+ up(&dir->i_sem);
+ return result;
}
+
+ /*
+ * Uhhuh! Nasty case: the cache was re-populated while
+ * we waited on the semaphore. Need to revalidate, but
+ * we're going to return this entry regardless (same
+ * as if it was busy).
+ */
up(&dir->i_sem);
+ if (result->d_op && result->d_op->d_revalidate)
+ result->d_op->d_revalidate(result, flags);
return result;
}
# define __raw_readl __readl
# define __raw_readq __readq
# define __raw_writeb __writeb
-# define __raw_writeb __writew
+# define __raw_writew __writew
# define __raw_writel __writel
# define __raw_writeq __writeq
extern unsigned long ___raw_readl(unsigned long addr);
extern unsigned long ___raw_readq(unsigned long addr);
extern void ___raw_writeb(unsigned char b, unsigned long addr);
-extern void ___raw_writeb(unsigned short b, unsigned long addr);
+extern void ___raw_writew(unsigned short b, unsigned long addr);
extern void ___raw_writel(unsigned int b, unsigned long addr);
extern void ___raw_writeq(unsigned long b, unsigned long addr);
#ifdef __raw_writeb
# define writeb(v,a) ({ __raw_writeb((v),(a)); mb(); })
#endif
-#ifdef __raw_writeb
-# define writew(v,a) ({ __raw_writeb((v),(a)); mb(); })
+#ifdef __raw_writew
+# define writew(v,a) ({ __raw_writew((v),(a)); mb(); })
#endif
#ifdef __raw_writel
# define writel(v,a) ({ __raw_writel((v),(a)); mb(); })
#ifndef __raw_writeb
# define __raw_writeb(v,a) ___raw_writeb((v),(unsigned long)(a))
#endif
-#ifndef __raw_writeb
-# define __raw_writeb(v,a) ___raw_writeb((v),(unsigned long)(a))
+#ifndef __raw_writew
+# define __raw_writew(v,a) ___raw_writew((v),(unsigned long)(a))
#endif
#ifndef __raw_writel
# define __raw_writel(v,a) ___raw_writel((v),(unsigned long)(a))
#define PageSkip(page) (0)
#define kern_addr_valid(addr) (1)
+#define io_remap_page_range(start, busaddr, size, prot) \
+ remap_page_range(start, virt_to_phys(ioremap(busaddr)), size, prot)
+
#endif /* _ALPHA_PGTABLE_H */
return c != 0;
}
+extern __inline__ int atomic_inc_and_test_greater_zero(volatile atomic_t *v)
+{
+ unsigned char c;
+
+ __asm__ __volatile__(
+ LOCK "incl %0; setg %1"
+ :"=m" (__atomic_fool_gcc(v)), "=qm" (c)
+ :"m" (__atomic_fool_gcc(v)));
+ return c; /* can be only 0 or 1 */
+}
+
/* These are x86-specific, used by some header files */
#define atomic_clear_mask(mask, addr) \
__asm__ __volatile__(LOCK "andl %0,%1" \
static inline int hardirq_trylock(int cpu)
{
- return !atomic_read(&global_irq_count) && !test_bit(0,&global_irq_lock);
+ return !local_irq_count[cpu] && !test_bit(0,&global_irq_lock);
}
#define hardirq_endlock(cpu) do { } while (0)
#define PageSkip(page) (0)
#define kern_addr_valid(addr) (1)
+#define io_remap_page_range remap_page_range
+
#endif /* _I386_PAGE_H */
*
* This is trivially done with load_locked/store_cond,
* but on the x86 we need an external synchronizer.
+ *
+ * NOTE: we can't look at the semaphore count here since it can be
+ * unreliable. Even if the count is minor than 1, the semaphore
+ * could be just owned by another process (this because not only up() increases
+ * the semaphore count, also the interruptible/trylock call can increment
+ * the semaphore count when they fails).
*/
static inline void wake_one_more(struct semaphore * sem)
{
unsigned long flags;
spin_lock_irqsave(&semaphore_wake_lock, flags);
- if (atomic_read(&sem->count) <= 0)
- sem->waking++;
+ sem->waking++;
spin_unlock_irqrestore(&semaphore_wake_lock, flags);
}
* 0 go to sleep
* -EINTR interrupted
*
- * We must undo the sem->count down_interruptible() increment while we are
- * protected by the spinlock in order to make atomic this atomic_inc() with the
- * atomic_read() in wake_one_more(), otherwise we can race. -arca
+ * If we give up we must undo our count-decrease we previously did in down().
+ * Subtle: up() can continue to happens and increase the semaphore count
+ * even during our critical section protected by the spinlock. So
+ * we must remeber to undo the sem->waking that will be run from
+ * wake_one_more() some time soon, if the semaphore count become > 0.
*/
static inline int waking_non_zero_interruptible(struct semaphore *sem,
struct task_struct *tsk)
sem->waking--;
ret = 1;
} else if (signal_pending(tsk)) {
- atomic_inc(&sem->count);
+ if (atomic_inc_and_test_greater_zero(&sem->count))
+ sem->waking--;
ret = -EINTR;
}
spin_unlock_irqrestore(&semaphore_wake_lock, flags);
* 1 failed to lock
* 0 got the lock
*
- * We must undo the sem->count down_trylock() increment while we are
- * protected by the spinlock in order to make atomic this atomic_inc() with the
- * atomic_read() in wake_one_more(), otherwise we can race. -arca
+ * Implementation details are the same of the interruptible case.
*/
static inline int waking_non_zero_trylock(struct semaphore *sem)
{
spin_lock_irqsave(&semaphore_wake_lock, flags);
if (sem->waking <= 0)
- atomic_inc(&sem->count);
- else {
+ {
+ if (atomic_inc_and_test_greater_zero(&sem->count))
+ sem->waking--;
+ } else {
sem->waking--;
ret = 0;
}
#define PageSkip(page) (0)
#define kern_addr_valid(addr) (1)
+#define io_remap_page_range remap_page_range
+
#endif /* _M68K_PGTABLE_H */
#define PageSkip(page) (0)
#define kern_addr_valid(addr) (1)
+#define io_remap_page_range remap_page_range
+
#endif __ASSEMBLY__
#endif /* _PPC_PGTABLE_H */
struct fb_fix_screeninfo {
char id[16]; /* identification string eg "TT Builtin" */
- char *smem_start; /* Start of frame buffer mem */
+ unsigned long smem_start; /* Start of frame buffer mem */
/* (physical address) */
__u32 smem_len; /* Length of frame buffer mem */
__u32 type; /* see FB_TYPE_* */
__u16 ypanstep; /* zero if no hardware panning */
__u16 ywrapstep; /* zero if no hardware ywrap */
__u32 line_length; /* length of a line in bytes */
- char *mmio_start; /* Start of Memory Mapped I/O */
+ unsigned long mmio_start; /* Start of Memory Mapped I/O */
/* (physical address) */
__u32 mmio_len; /* Length of Memory Mapped I/O */
__u32 accel; /* Type of acceleration available */
* elsewhere, in preparation for a serial line console (someday).
* Ted Ts'o, 2/11/93.
* Modified for sysctl support, 1/8/97, Chris Horn.
+ * Fixed SMP synchronization, 08/08/99, Manfred Spraul
+ * manfreds@colorfullife.com
*/
#include <linux/mm.h>
#include <asm/uaccess.h>
#define LOG_BUF_LEN (16384)
+#define LOG_BUF_MASK (LOG_BUF_LEN-1)
static char buf[1024];
int minimum_console_loglevel = MINIMUM_CONSOLE_LOGLEVEL;
int default_console_loglevel = DEFAULT_CONSOLE_LOGLEVEL;
+spinlock_t console_lock = SPIN_LOCK_UNLOCKED;
+
struct console *console_drivers = NULL;
static char log_buf[LOG_BUF_LEN];
static unsigned long log_start = 0;
static unsigned long logged_chars = 0;
struct console_cmdline console_cmdline[MAX_CMDLINECONSOLES];
static int preferred_console = -1;
-spinlock_t console_lock = SPIN_LOCK_UNLOCKED;
/*
* Setup a list of consoles. Called from init/main.c
*/
int do_syslog(int type, char * buf, int len)
{
- unsigned long i, j, count;
+ unsigned long i, j, limit, count;
int do_clear = 0;
char c;
int error = -EPERM;
i = 0;
spin_lock_irq(&console_lock);
while (log_size && i < len) {
- c = *((char *) log_buf+log_start);
+ c = log_buf[log_start & LOG_BUF_MASK];
log_start++;
log_size--;
- log_start &= LOG_BUF_LEN-1;
spin_unlock_irq(&console_lock);
__put_user(c,buf);
buf++;
error = verify_area(VERIFY_WRITE,buf,len);
if (error)
goto out;
+ spin_lock_irq(&console_lock);
count = len;
if (count > LOG_BUF_LEN)
count = LOG_BUF_LEN;
- /* The logged_chars, log_start, and log_size are serialized
- by the console_lock (the console_lock can be acquired also
- from irqs by printk). */
- spin_lock_irq(&console_lock);
if (count > logged_chars)
count = logged_chars;
- j = log_start + log_size - count;
- spin_unlock_irq(&console_lock);
- /* While writing data to the userspace buffer printk may
- trash our information but the _only_ thing we care is to
- have a coherent `j' value. */
- for (i = 0; i < count; i++) {
- c = *((char *) log_buf+(j++ & (LOG_BUF_LEN-1)));
- __put_user(c, buf++);
- }
if (do_clear)
- {
- /* the increment done in printk may undo our
- not atomic assigment if we do it without the
- console lock held. */
- spin_lock_irq(&console_lock);
logged_chars = 0;
+ limit = log_start + log_size;
+ /*
+ * __put_user() could sleep, and while we sleep
+ * printk() could overwrite the messages
+ * we try to copy to user space. Therefore
+ * the messages are copied in reverse. <manfreds>
+ */
+ for(i=0;i < count;i++) {
+ j = limit-1-i;
+ if (j+LOG_BUF_LEN < log_start+log_size)
+ break;
+ c = log_buf[ j & LOG_BUF_MASK ];
spin_unlock_irq(&console_lock);
+ __put_user(c,&buf[count-1-i]);
+ spin_lock_irq(&console_lock);
}
+ spin_unlock_irq(&console_lock);
error = i;
+ if(i != count) {
+ int offset = count-error;
+ /* buffer overflow during copy, correct user buffer. */
+ for(i=0;i<error;i++) {
+ __get_user(c,&buf[i+offset]);
+ __put_user(c,&buf[i]);
+ }
+ }
+
break;
case 5: /* Clear ring buffer */
spin_lock_irq(&console_lock);
error = -EINVAL;
if (len < 1 || len > 8)
goto out;
- spin_lock_irq(&console_lock);
if (len < minimum_console_loglevel)
len = minimum_console_loglevel;
+ spin_lock_irq(&console_lock);
console_loglevel = len;
spin_unlock_irq(&console_lock);
error = 0;
return do_syslog(type, buf, len);
}
-
asmlinkage int printk(const char *fmt, ...)
{
va_list args;
}
line_feed = 0;
for (; p < buf_end; p++) {
- log_buf[(log_start+log_size) & (LOG_BUF_LEN-1)] = *p;
+ log_buf[(log_start+log_size) & LOG_BUF_MASK] = *p;
if (log_size < LOG_BUF_LEN)
log_size++;
- else {
+ else
log_start++;
- log_start &= LOG_BUF_LEN-1;
- }
+
logged_chars++;
if (*p == '\n') {
line_feed = 1;
void console_print(const char *s)
{
- struct console *c = console_drivers;
+ struct console *c;
+ unsigned long flags;
int len = strlen(s);
- spin_lock_irq(&console_lock);
+ spin_lock_irqsave(&console_lock,flags);
+ c = console_drivers;
while(c) {
if ((c->flags & CON_ENABLED) && c->write)
c->write(c, s, len);
c = c->next;
}
- spin_unlock_irq(&console_lock);
+ spin_unlock_irqrestore(&console_lock,flags);
}
void unblank_console(void)
{
- struct console *c = console_drivers;
-
- spin_lock_irq(&console_lock);
+ struct console *c;
+ unsigned long flags;
+
+ spin_lock_irqsave(&console_lock,flags);
+ c = console_drivers;
while(c) {
if ((c->flags & CON_ENABLED) && c->unblank)
c->unblank();
c = c->next;
}
- spin_unlock_irq(&console_lock);
+ spin_unlock_irqrestore(&console_lock,flags);
}
/*
*/
void register_console(struct console * console)
{
- int i,j,len;
+ int i, j,len;
int p;
char buf[16];
signed char msg_level = -1;
char *q;
+ unsigned long flags;
- spin_lock_irq(&console_lock);
/*
* See if we want to use this console driver. If we
* didn't select a console we take the first one
}
if (!(console->flags & CON_ENABLED))
- goto out;
+ return;
/*
* Put this console in the list - keep the
* preferred driver at the head of the list.
*/
+ spin_lock_irqsave(&console_lock,flags);
if ((console->flags & CON_CONSDEV) || console_drivers == NULL) {
console->next = console_drivers;
console_drivers = console;
console->next = console_drivers->next;
console_drivers->next = console;
}
- if ((console->flags & CON_PRINTBUFFER) == 0) goto out;
-
+ if ((console->flags & CON_PRINTBUFFER) == 0)
+ goto done;
/*
* Print out buffered log messages.
*/
- for (p=log_start,i=0,j=0; i < log_size; i++) {
+ p = log_start & LOG_BUF_MASK;
+
+ for (i=0,j=0; i < log_size; i++) {
buf[j++] = log_buf[p];
- p++; p &= LOG_BUF_LEN-1;
+ p = (p+1) & LOG_BUF_MASK;
if (buf[j-1] != '\n' && i < log_size - 1 && j < sizeof(buf)-1)
continue;
buf[j] = 0;
q = buf;
len = j;
if (msg_level < 0) {
- msg_level = buf[1] - '0';
- q = buf + 3;
- len -= 3;
+ if(buf[0] == '<' &&
+ buf[1] >= '0' &&
+ buf[1] <= '7' &&
+ buf[2] == '>') {
+ msg_level = buf[1] - '0';
+ q = buf + 3;
+ len -= 3;
+ } else
+ {
+ msg_level = default_message_loglevel;
+ }
}
if (msg_level < console_loglevel)
console->write(console, q, len);
msg_level = -1;
j = 0;
}
- out:
- spin_unlock_irq(&console_lock);
+done:
+ spin_unlock_irqrestore(&console_lock,flags);
}
int unregister_console(struct console * console)
{
struct console *a,*b;
- int ret = 0;
-
- spin_lock_irq(&console_lock);
+ unsigned long flags;
+ int res = 1;
+
+ spin_lock_irqsave(&console_lock,flags);
if (console_drivers == console) {
console_drivers=console->next;
- goto out;
- }
- for (a=console_drivers->next, b=console_drivers ;
- a; b=a, a=b->next) {
- if (a == console) {
- b->next = a->next;
- goto out;
- }
+ res = 0;
+ } else
+ {
+ for (a=console_drivers->next, b=console_drivers ;
+ a; b=a, a=b->next) {
+ if (a == console) {
+ b->next = a->next;
+ res = 0;
+ break;
+ }
+ }
}
- ret = 1;
- out:
- spin_unlock_irq(&console_lock);
- return ret;
+
+ spin_unlock_irqrestore(&console_lock,flags);
+ return res;
}
/*
return goodness(p, cpu, prev->mm) - goodness(prev, cpu, prev->mm);
}
-/*
- * If there is a dependency between p1 and p2,
- * don't be too eager to go into the slow schedule.
- * In particular, if p1 and p2 both want the kernel
- * lock, there is no point in trying to make them
- * extremely parallel..
- *
- * (No lock - lock_depth < 0)
- *
- * There are two additional metrics here:
- *
- * first, a 'cutoff' interval, currently 0-200 usecs on
- * x86 CPUs, depending on the size of the 'SMP-local cache'.
- * If the current process has longer average timeslices than
- * this, then we utilize the idle CPU.
- *
- * second, if the wakeup comes from a process context,
- * then the two processes are 'related'. (they form a
- * 'gang')
- *
- * An idle CPU is almost always a bad thing, thus we skip
- * the idle-CPU utilization only if both these conditions
- * are true. (ie. a 'process-gang' rescheduling with rather
- * high frequency should stay on the same CPU).
- *
- * [We can switch to something more finegrained in 2.3.]
- *
- * do not 'guess' if the to-be-scheduled task is RT.
- */
-#define related(p1,p2) (((p1)->lock_depth >= 0) && (p2)->lock_depth >= 0) && \
- (((p2)->policy == SCHED_OTHER) && ((p1)->avg_slice < cacheflush_time))
-
-static inline void reschedule_idle_slow(struct task_struct * p)
+static void reschedule_idle(struct task_struct * p)
{
#ifdef __SMP__
-/*
- * (see reschedule_idle() for an explanation first ...)
- *
- * Pass #2
- *
- * We try to find another (idle) CPU for this woken-up process.
- *
- * On SMP, we mostly try to see if the CPU the task used
- * to run on is idle.. but we will use another idle CPU too,
- * at this point we already know that this CPU is not
- * willing to reschedule in the near future.
- *
- * An idle CPU is definitely wasted, especially if this CPU is
- * running long-timeslice processes. The following algorithm is
- * pretty good at finding the best idle CPU to send this process
- * to.
- *
- * [We can try to preempt low-priority processes on other CPUs in
- * 2.3. Also we can try to use the avg_slice value to predict
- * 'likely reschedule' events even on other CPUs.]
- */
int this_cpu = smp_processor_id(), target_cpu;
struct task_struct *tsk, *target_tsk;
- int cpu, best_cpu, weight, best_weight, i;
+ int cpu, best_cpu, i;
unsigned long flags;
- best_weight = 0; /* prevents negative weight */
-
spin_lock_irqsave(&runqueue_lock, flags);
/*
for (i = 0; i < smp_num_cpus; i++) {
cpu = cpu_logical_map(i);
tsk = cpu_curr(cpu);
- if (related(tsk, p))
- goto out_no_target;
- weight = preemption_goodness(tsk, p, cpu);
- if (weight > best_weight) {
- best_weight = weight;
+ if (tsk == idle_task(cpu))
target_tsk = tsk;
- }
}
+ if (target_tsk && p->avg_slice > cacheflush_time)
+ goto send_now;
+
+ tsk = cpu_curr(best_cpu);
+ if (preemption_goodness(tsk, p, best_cpu) > 0)
+ target_tsk = tsk;
+
/*
* found any suitable CPU?
*/
#endif
}
-static void reschedule_idle(struct task_struct * p)
-{
-#ifdef __SMP__
- int cpu = smp_processor_id();
- /*
- * ("wakeup()" should not be called before we've initialized
- * SMP completely.
- * Basically a not-yet initialized SMP subsystem can be
- * considered as a not-yet working scheduler, simply dont use
- * it before it's up and running ...)
- *
- * SMP rescheduling is done in 2 passes:
- * - pass #1: faster: 'quick decisions'
- * - pass #2: slower: 'lets try and find a suitable CPU'
- */
-
- /*
- * Pass #1. (subtle. We might be in the middle of __switch_to, so
- * to preserve scheduling atomicity we have to use cpu_curr)
- */
- if ((p->processor == cpu) && related(cpu_curr(cpu), p))
- return;
-#endif /* __SMP__ */
- /*
- * Pass #2
- */
- reschedule_idle_slow(p);
-}
-
/*
* Careful!
*
* because there really aren't any performance issues here
* and we need to check for errors.
*/
- if (!PageLocked(page))
- PAGE_BUG(page);
+ lock_page(page);
+ if (Page_Uptodate(page)) {
+ UnlockPage(page);
+ goto success;
+ }
ClearPageError(page);
error = inode->i_op->readpage(file, page);
if (error)
wait_on_page(map);
}
- if (++repeat < 16)
+ if (++repeat < 16) {
+ ptr = va & PAGE_MASK;
goto repeat;
+ }
return -EAGAIN;
}
while (List!=NULL)
{
- if (strstr(List->value,Filename)!=NULL)
+ if (strstr(Filename,List->value)!=NULL)
{
if (filp!=NULL)
fput(filp);
* I make simple dependency lines for #include <*.h> and #include "*.h".
* I also find instances of CONFIG_FOO and generate dependencies
* like include/config/foo.h.
+ *
+ * 1 August 1999, Michael Elizabeth Chastain, <mec@shout.net>
+ * - Keith Owens reported a bug in smart config processing. There used
+ * to be an optimization for "#define CONFIG_FOO ... #ifdef CONFIG_FOO",
+ * so that the file would not depend on CONFIG_FOO because the file defines
+ * this symbol itself. But this optimization is bogus! Consider this code:
+ * "#if 0 \n #define CONFIG_FOO \n #endif ... #ifdef CONFIG_FOO". Here
+ * the definition is inactivated, but I still used it. It turns out this
+ * actually happens a few times in the kernel source. The simple way to
+ * fix this problem is to remove this particular optimization.
*/
#include <ctype.h>
/*
* Add a new value to the configuration string.
*/
-void define_config(int convert, const char * name, int len)
+void define_config(const char * name, int len)
{
grow_config(len + 1);
memcpy(str_config+len_config, name, len);
-
- if (convert) {
- int i;
- for (i = 0; i < len; i++) {
- char c = str_config[len_config+i];
- if (isupper(c)) c = tolower(c);
- if (c == '_') c = '/';
- str_config[len_config+i] = c;
- }
- }
-
len_config += len;
str_config[len_config++] = '\n';
}
void clear_config(void)
{
len_config = 0;
- define_config(0, "", 0);
+ define_config("", 0);
}
return;
if (len >= 7 && !memcmp(name, "config/", 7))
- define_config(0, name+7, len-7-2);
+ define_config(name+7, len-7-2);
memcpy(path->buffer+path->len, name, len);
path->buffer[path->len+len] = '\0';
if (is_defined_config(pc, len))
return;
- define_config(0, pc, len);
+ define_config(pc, len);
if (!hasdep) {
hasdep = 1;
GETNEXT NOTCASE('f', __start);
goto pound_define_undef;
-/* #\s*(define|undef)\s*CONFIG_(\w*) */
+/*
+ * #\s*(define|undef)\s*CONFIG_(\w*)
+ *
+ * this does not define the word, because it could be inside another
+ * conditional (#if 0). But I do parse the word so that this instance
+ * does not count as a use. -- mec
+ */
pound_define_undef:
GETNEXT
CASE(' ', pound_define_undef);
GETNEXT
if (isalnum(current) || current == '_')
goto pound_define_undef_CONFIG_word;
- define_config(1, map_dot, next - map_dot - 1);
goto __start;
/* \<CONFIG_(\w*) */