Commit 507e819f authored by Linus Torvalds's avatar Linus Torvalds

Import 2.1.45pre10

parent ca22d2b1
......@@ -81,6 +81,14 @@ S: University of Notre Dame
S: Notre Dame, Indiana
S: USA
N: James Banks
E: james.banks@caldera.com
D: TLAN network driver
S: Caldera, Inc.
S: 633 South 550 East
S: Provo, UT 84606
S: USA
N: Peter Bauer
E: 100136.3530@compuserve.com
D: Driver for depca-ethernet-board
......@@ -971,12 +979,13 @@ S: D-91056 Erlangen
S: Germany
N: Michael Meskes
E: meskes@informatik.rwth-aachen.de
E: meskes@topsystem.de
P: 1024/04B6E8F5 6C 77 33 CA CC D6 22 03 AB AB 15 A3 AE AD 39 7D
D: Kernel hacker. Software watchdog daemon.
D: Maintainer of several Debian packages
S: Lehrstuhl fuer angewandte Mathematik insb. Informatik
S: RWTH-Aachen
S: D-52056 Aachen
S: topsystem Systemhaus GmbH
S: Europark A2, Adenauerstr. 20
S: D-52146 Wuerselen
S: Germany
N: Nigel Metheringham
......
......@@ -3308,6 +3308,14 @@ CONFIG_ETH16I
Multiple-Ethernet-mini-HOWTO, available from
sunsite.unc.edu:/pub/Linux/docs/HOWTO/mini.
TI ThunderLAN support (EXPERIMENTAL)
CONFIG_TLAN
If you have a TLAN based network card which is supported by this
driver, say Y and read the Ethernet-HOWTO. Devices currently supported
are the Compaq Netelligent 10, Netelligent 10/100, and Internal
NetFlex 3. This driver is also available as a module. Please email
feedback to james.banks@caldera.com.
Zenith Z-Note support
CONFIG_ZNET
The Zenith Z-Note notebook computer has a built-in network
......@@ -4385,6 +4393,12 @@ CONFIG_82C710_MOUSE
doesn't work. Read the Busmouse-HOWTO, available via ftp (user:
anonymous) in sunsite.unc.edu:/pub/Linux/docs/HOWTO.
PC110 digitizer pad support
CONFIG_PC110_PAD
This drives the digitizer pad on the IBM PC110 palmtop (see
http://toy.cabi.net). It can turn the digitizer pad into a
mouse emulation with tap gestures or into an absolute pad.
Microsoft busmouse support
CONFIG_MS_BUSMOUSE
These animals (also called Inport mice) are connected to an
......
------------------------------------------------------------------------------
WAN Router for Linux Operating System
------------------------------------------------------------------------------
Version 1.0.0
December 31, 1996
Author: Gene Kozin <genek@compuserve.com>
Copyright (c) 1995-1996 Sangoma Technologies Inc.
Version 1.0.3 - June 3, 1997
Version 1.0.1 - January 30, 1997
Author: Jaspreet Singh <jaspreet@sangoma.com>
Gene Kozin <genek@compuserve.com>
Copyright (c) 1995-1997 Sangoma Technologies Inc.
------------------------------------------------------------------------------
INTRODUCTION
......@@ -95,12 +96,6 @@ Ave, Cambridge, MA 02139, USA.
KNOWN BUGS AND LIMITATIONS
/proc user interface is not complete yet.
ACKNOLEGEMENTS
This product is based on the WANPIPE(tm) Multiprotocol WAN Router developed
......@@ -122,9 +117,19 @@ product.
REVISION HISTORY
1.0.3 June 3, 1997
o UDP port for multiple boards (Frame relay, PPP)
o Continuous Transmission of Configure Request Packet for PPP (this
support is only added for 508 cards)
o Connection Timeout for PPP changed from 900 to 0
o Flow Control for multiple boards and multiple channels (Frame Relay)
1.0.1 January 30, 1997
o Implemented user-readable status and statistics via /proc filesystem
1.0.0 December 31, 1996
1.0.0 December 31, 1996
--------------------------
o Initial version.
o Initial version
>>>>>> END <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
......@@ -95,6 +95,12 @@ M: phil@tazenda.demon.co.uk
L: linux-net@vger.rutgers.edu
S: Maintained
TLAN NETWORK DRIVER
P: James Banks
M: james.banks@caldera.com
L: linux-net@vger.rutgers.edu
S: Supported
DIGI RIGHTSWITCH NETWORK DRIVER
P: Rick Richardson
M: rick@dgii.com
......@@ -222,10 +228,10 @@ L: linux-tape@vger.rutgers.edu
S: Maintained
IPX NETWORK LAYER
P: Alan Cox [for the moment]
M: net-patches@lxorguk.ukuu.org.uk
L: linux-ipx@vger.rutgers.edu [will change]
S: Maintained
P:
M:
L:
S: Orphan
IDE DRIVER [GENERAL]
P: Mark Lord
......@@ -285,10 +291,10 @@ L: linux-hams@vger.rutgers.edu
S: Maintained
NETWORKING [GENERAL]:
P: Alan Cox
M: net-patches@lxorguk.ukuu.org.uk
P: Networking Teak
M: netdev@nuclecu.unam.mx
L: linux-net@vger.rutgers.edu
W: http://www.uk.linux.org/NetNews.html
W: http://www.uk.linux.org/NetNews.html (2.0 only)
S: Maintained
NETWORKING [IPv4/IPv6]:
......@@ -331,8 +337,8 @@ L: samba@listproc.anu.edu.au
S: Maintained
SMP: (except SPARC)
P: Alan Cox
M: smp-patches@lxorguk.ukuu.org.uk
P: Linus Torvalds
M: torvalds@transmeta.com
L: linux-smp@vger.rutgers.edu
S: Maintained
......
......@@ -227,12 +227,14 @@ CONFIG_MOUSE=y
# CONFIG_MS_BUSMOUSE is not set
CONFIG_PSMOUSE=y
CONFIG_82C710_MOUSE=y
# CONFIG_PC110_PAD is not set
# CONFIG_UMISC is not set
# CONFIG_QIC02_TAPE is not set
# CONFIG_FTAPE is not set
# CONFIG_APM is not set
# CONFIG_WATCHDOG is not set
# CONFIG_RTC is not set
# CONFIG_JOYSTICK is not set
#
# Sound
......
/*
* bios32.c - BIOS32, PCI BIOS functions.
*
* $Id: bios32.c,v 1.11 1997/05/07 13:35:21 mj Exp $
* $Id: bios32.c,v 1.12 1997/06/26 13:33:46 mj Exp $
*
* Sponsored by
* iX Multiuser Multitasking Magazine
......@@ -59,6 +59,8 @@
*
* May 7, 1997 : Added some missing cli()'s. [mj]
*
* Jun 20, 1997 : Corrected problems in "conf1" type accesses.
* (paubert@iram.es)
*/
#include <linux/config.h>
......@@ -512,16 +514,7 @@ static int pci_conf1_read_config_byte(unsigned char bus, unsigned char device_fn
save_flags(flags); cli();
outl(CONFIG_CMD(bus,device_fn,where), 0xCF8);
switch (where & 3) {
case 0: *value = inb(0xCFC);
break;
case 1: *value = inb(0xCFD);
break;
case 2: *value = inb(0xCFE);
break;
case 3: *value = inb(0xCFF);
break;
}
*value = inb(0xCFC + (where&3));
restore_flags(flags);
return PCIBIOS_SUCCESSFUL;
}
......@@ -531,12 +524,10 @@ static int pci_conf1_read_config_word (unsigned char bus,
{
unsigned long flags;
if (where&1) return PCIBIOS_BAD_REGISTER_NUMBER;
save_flags(flags); cli();
outl(CONFIG_CMD(bus,device_fn,where), 0xCF8);
if (where & 2)
*value = inw(0xCFE);
else
*value = inw(0xCFC);
*value = inw(0xCFC + (where&2));
restore_flags(flags);
return PCIBIOS_SUCCESSFUL;
}
......@@ -546,6 +537,7 @@ static int pci_conf1_read_config_dword (unsigned char bus, unsigned char device_
{
unsigned long flags;
if (where&3) return PCIBIOS_BAD_REGISTER_NUMBER;
save_flags(flags); cli();
outl(CONFIG_CMD(bus,device_fn,where), 0xCF8);
*value = inl(0xCFC);
......@@ -560,7 +552,7 @@ static int pci_conf1_write_config_byte (unsigned char bus, unsigned char device_
save_flags(flags); cli();
outl(CONFIG_CMD(bus,device_fn,where), 0xCF8);
outb(value, 0xCFC);
outb(value, 0xCFC + (where&3));
restore_flags(flags);
return PCIBIOS_SUCCESSFUL;
}
......@@ -570,9 +562,10 @@ static int pci_conf1_write_config_word (unsigned char bus, unsigned char device_
{
unsigned long flags;
if (where&1) return PCIBIOS_BAD_REGISTER_NUMBER;
save_flags(flags); cli();
outl(CONFIG_CMD(bus,device_fn,where), 0xCF8);
outw(value, 0xCFC);
outw(value, 0xCFC + (where&2));
restore_flags(flags);
return PCIBIOS_SUCCESSFUL;
}
......@@ -582,6 +575,7 @@ static int pci_conf1_write_config_dword (unsigned char bus, unsigned char device
{
unsigned long flags;
if (where&3) return PCIBIOS_BAD_REGISTER_NUMBER;
save_flags(flags); cli();
outl(CONFIG_CMD(bus,device_fn,where), 0xCF8);
outl(value, 0xCFC);
......
......@@ -244,6 +244,17 @@ static const char * i586model(unsigned int nr)
return NULL;
}
static const char * k5model(unsigned int nr)
{
static const char *model[] = {
"SSA5 (PR-75, PR-90, PR-100)", "5k86 (PR-120, PR-133)",
"5k86 (PR-166)", "5k86 (PR-200)", "", "", "K6"
};
if (nr < sizeof(model)/sizeof(char *))
return model[nr];
return NULL;
}
static const char * i686model(unsigned int nr)
{
static const char *model[] = {
......@@ -263,7 +274,11 @@ static const char * getmodel(int x86, int model)
p = i486model(model);
break;
case 5:
p = i586model(model);
if(strcmp(x86_vendor_id, "AuthenticAMD") == 0){
p = k5model(model);
} else {
p = i586model(model);
}
break;
case 6:
p = i686model(model);
......
# $Id: Makefile,v 1.28 1997/05/01 01:41:21 davem Exp $
# $Id: Makefile,v 1.29 1997/07/11 11:05:23 jj Exp $
# sparc/Makefile
#
# Makefile for the architecture dependent flags and dependencies on the
......@@ -45,3 +45,6 @@ archdep:
check_asm:
$(MAKE) -C arch/sparc/kernel check_asm
tftpboot.img:
$(MAKE) -C arch/sparc/boot tftpboot.img
# $Id: Makefile,v 1.3 1996/08/04 08:40:58 ecd Exp $
# Makefile for the Sparc low level /boot module.
# $Id: Makefile,v 1.4 1997/07/11 11:05:18 jj Exp $
# Makefile for the Sparc boot stuff.
#
# Copyright (C) 1995 David S. Miller (davem@caip.rutgers.edu)
# Copyright (C) 1997 Jakub Jelinek (jj@sunsite.mff.cuni.cz)
ROOT_IMG =/usr/src/root.img
ELFTOAOUT =elftoaout
all: boot
boot:
@echo "Nothing special to be done for 'boot' on Linux/SPARC."
tftpboot.img: piggyback
$(ELFTOAOUT) $(TOPDIR)/vmlinux -o tftpboot.img
./piggyback tftpboot.img $(TOPDIR)/System.map $(ROOT_IMG)
piggyback: piggyback.c
$(HOSTCC) $(HOSTCFLAGS) -o piggyback piggyback.c
dep:
/* $Id: piggyback.c,v 1.1 1997/07/11 11:05:17 jj Exp $
Simple utility to make a single-image install kernel with initial ramdisk
for Sparc tftpbooting without need to set up nfs.
Copyright (C) 1996 Jakub Jelinek (jj@sunsite.mff.cuni.cz)
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include <errno.h>
#include <fcntl.h>
#include <dirent.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
/* Note: run this on an a.out kernel (use elftoaout for it), as PROM looks for a.out image onlly
usage: piggyback vmlinux System.map tail, where tail is gzipped fs of the initial ramdisk */
void die(char *str)
{
perror (str);
exit(1);
}
int main(int argc,char **argv)
{
char buffer [1024], *q, *r;
unsigned int i, j, k, start, end, offset;
FILE *map;
struct stat s;
int image, tail;
if (stat (argv[3], &s) < 0) die (argv[3]);
map = fopen (argv[2], "r");
if (!map) die(argv[2]);
while (fgets (buffer, 1024, map)) {
if (!strcmp (buffer + 11, "start\n"))
start = strtoul (buffer, NULL, 16);
else if (!strcmp (buffer + 11, "end\n"))
end = strtoul (buffer, NULL, 16);
}
fclose (map);
if ((image = open(argv[1],O_RDWR)) < 0) die(argv[1]);
if (read(image,buffer,512) != 512) die(argv[1]);
if (!memcmp (buffer, "\177ELF", 4)) {
unsigned int *p = (unsigned int *)(buffer + *(unsigned int *)(buffer + 28));
i = p[1] + *(unsigned int *)(buffer + 24) - p[2];
if (lseek(image,i,0) < 0) die("lseek");
if (read(image,buffer,512) != 512) die(argv[1]);
j = 0;
} else if (*(unsigned int *)buffer == 0x01030107) {
i = j = 32;
} else {
fprintf (stderr, "Not ELF nor a.out. Don't blame me.\n");
exit(1);
}
k = i;
i += ((*(unsigned short *)(buffer + j + 2))<<2) - 512;
if (lseek(image,i,0) < 0) die("lseek");
if (read(image,buffer,1024) != 1024) die(argv[1]);
for (q = buffer, r = q + 512; q < r; q += 4) {
if (*q == 'H' && q[1] == 'd' && q[2] == 'r' && q[3] == 'S')
break;
}
if (q == r) {
fprintf (stderr, "Couldn't find headers signature in the kernel.\n");
exit(1);
}
offset = i + (q - buffer) + 10;
if (lseek(image, offset, 0) < 0) die ("lseek");
*(unsigned *)buffer = 0;
*(unsigned *)(buffer + 4) = 0x01000000;
*(unsigned *)(buffer + 8) = ((end + 32 + 4095) & ~4095);
*(unsigned *)(buffer + 12) = s.st_size;
if (write(image,buffer+2,14) != 14) die (argv[1]);
if (lseek(image, k - start + ((end + 32 + 4095) & ~4095), 0) < 0) die ("lseek");
if ((tail = open(argv[3],O_RDONLY)) < 0) die(argv[3]);
while ((i = read (tail,buffer,1024)) > 0)
if (write(image,buffer,i) != i) die (argv[1]);
if (close(image) < 0) die("close");
if (close(tail) < 0) die("close");
return 0;
}
......@@ -42,7 +42,7 @@ SUN_FB_CGFOURTEEN=y
SUN_FB_BWTWO=y
SUN_FB_LEO=y
TADPOLE_FB_WEITEK=y
SUN_FB_CREATOR=y
#SUN_FB_CREATOR is not set
#
# Misc Linux/SPARC drivers
......
......@@ -594,8 +594,9 @@ asmlinkage int sparc_execve(struct pt_regs *regs)
base = 1;
lock_kernel();
error = getname((char *) regs->u_regs[base + UREG_I0], &filename);
if(error)
filename = getname((char *)regs->u_regs[base + UREG_I0]);
error = PTR_ERR(filename);
if(IS_ERR(filename))
goto out;
error = do_execve(filename, (char **) regs->u_regs[base + UREG_I1],
(char **) regs->u_regs[base + UREG_I2], regs);
......
......@@ -90,10 +90,12 @@ asmlinkage unsigned long sunos_mmap(unsigned long addr, unsigned long len,
* of /dev/zero, transform it into an anonymous mapping.
* SunOS is so stupid some times... hmph!
*/
if(MAJOR(file->f_inode->i_rdev) == MEM_MAJOR &&
MINOR(file->f_inode->i_rdev) == 5) {
flags |= MAP_ANONYMOUS;
file = 0;
if(file->f_dentry && file->f_dentry->d_inode) {
if(MAJOR(file->f_dentry->d_inode->i_rdev) == MEM_MAJOR &&
MINOR(file->f_dentry->d_inode->i_rdev) == 5) {
flags |= MAP_ANONYMOUS;
file = 0;
}
}
if(!(flags & MAP_FIXED))
addr = 0;
......@@ -428,16 +430,32 @@ static int sunos_filldir(void * __buf, const char * name, int namlen,
asmlinkage int sunos_getdents(unsigned int fd, void * dirent, int cnt)
{
struct file * file;
struct dentry * dentry;
struct inode * inode;
struct sunos_dirent * lastdirent;
struct sunos_dirent_callback buf;
int error = -EBADF;
lock_kernel();
if (fd >= SUNOS_NR_OPEN || !(file = current->files->fd[fd]))
if(fd >= SUNOS_NR_OPEN)
goto out;
file = current->files->fd[fd];
if(!file)
goto out;
dentry = file->f_dentry;
if(!dentry)
goto out;
inode = dentry->d_inode;
if(!inode)
goto out;
error = -ENOTDIR;
if (!file->f_op || !file->f_op->readdir)
goto out;
error = -EINVAL;
if(cnt < (sizeof(struct sunos_dirent) + 255))
goto out;
......@@ -446,13 +464,12 @@ asmlinkage int sunos_getdents(unsigned int fd, void * dirent, int cnt)
buf.previous = NULL;
buf.count = cnt;
buf.error = 0;
error = file->f_op->readdir(file->f_inode, file, &buf, sunos_filldir);
error = file->f_op->readdir(inode, file, &buf, sunos_filldir);
if (error < 0)
goto out;
lastdirent = buf.previous;
if (!lastdirent) {
error = buf.error;
} else {
error = buf.error;
if (lastdirent) {
put_user(file->f_pos, &lastdirent->d_off);
error = cnt - buf.count;
}
......@@ -503,16 +520,32 @@ static int sunos_filldirentry(void * __buf, const char * name, int namlen,
asmlinkage int sunos_getdirentries(unsigned int fd, void * dirent, int cnt, unsigned int *basep)
{
struct file * file;
struct dentry * dentry;
struct inode * inode;
struct sunos_direntry * lastdirent;
struct sunos_direntry_callback buf;
int error = -EBADF;
lock_kernel();
if (fd >= SUNOS_NR_OPEN || !(file = current->files->fd[fd]))
if(fd >= SUNOS_NR_OPEN)
goto out;
file = current->files->fd[fd];
if(!file)
goto out;
dentry = file->f_dentry;
if(!dentry)
goto out;
inode = dentry->d_inode;
if(!inode)
goto out;
error = -ENOTDIR;
if (!file->f_op || !file->f_op->readdir)
goto out;
error = -EINVAL;
if(cnt < (sizeof(struct sunos_direntry) + 255))
goto out;
......@@ -521,13 +554,12 @@ asmlinkage int sunos_getdirentries(unsigned int fd, void * dirent, int cnt, unsi
buf.previous = NULL;
buf.count = cnt;
buf.error = 0;
error = file->f_op->readdir(file->f_inode, file, &buf, sunos_filldirentry);
error = file->f_op->readdir(inode, file, &buf, sunos_filldirentry);
if (error < 0)
goto out;
lastdirent = buf.previous;
if (!lastdirent) {
error = buf.error;
} else {
error = buf.error;
if (lastdirent) {
put_user(file->f_pos, basep);
error = cnt - buf.count;
}
......@@ -725,12 +757,13 @@ sunos_nfs_get_server_fd (int fd, struct sockaddr_in *addr)
int try_port;
int ret;
struct socket *socket;
struct dentry *dentry;
struct inode *inode;
struct file *file;
file = current->files->fd [fd];
inode = file->f_inode;
if (!inode || !inode->i_sock)
dentry = file->f_dentry;
if(!dentry || !(inode = dentry->d_inode))
return 0;
socket = &inode->u.socket_i;
......
# $Id: Makefile,v 1.19 1997/06/26 12:48:45 jj Exp $
# $Id: Makefile,v 1.20 1997/07/11 11:05:29 jj Exp $
# sparc64/Makefile
#
# Makefile for the architecture dependent flags and dependencies on the
......@@ -49,3 +49,6 @@ archdep:
check_asm:
$(MAKE) -C arch/sparc64/kernel check_asm
tftpboot.img:
$(MAKE) -C arch/sparc64/boot tftpboot.img
# $Id: Makefile,v 1.1 1997/07/11 11:05:25 jj Exp $
# Makefile for the Sparc64 boot stuff.
#
# Copyright (C) 1995 David S. Miller (davem@caip.rutgers.edu)
# Copyright (C) 1997 Jakub Jelinek (jj@sunsite.mff.cuni.cz)
ROOT_IMG =/usr/src/root.img
ELFTOAOUT =elftoaout
all: boot
boot:
@echo "Nothing special to be done for 'boot' on Linux/UltraSPARC."
tftpboot.img: piggyback
$(ELFTOAOUT) $(TOPDIR)/vmlinux -o tftpboot.img
./piggyback tftpboot.img $(TOPDIR)/System.map $(ROOT_IMG)
piggyback: piggyback.c
$(HOSTCC) $(HOSTCFLAGS) -o piggyback piggyback.c
dep:
/* $Id: piggyback.c,v 1.1 1997/07/11 11:05:26 jj Exp $
Simple utility to make a single-image install kernel with initial ramdisk
for Sparc64 tftpbooting without need to set up nfs.
Copyright (C) 1997 Jakub Jelinek (jj@sunsite.mff.cuni.cz)
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#include <stdio.h>
#include <string.h>
#include <ctype.h>
#include <errno.h>
#include <fcntl.h>
#include <dirent.h>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
/* Note: run this on an a.out kernel (use elftoaout for it), as PROM looks for a.out image onlly
usage: piggyback vmlinux System.map tail, where tail is gzipped fs of the initial ramdisk */
void die(char *str)
{
perror (str);
exit(1);
}
int main(int argc,char **argv)
{
char buffer [1024], *q, *r;
unsigned int i, j, k, start, end, offset;
FILE *map;
struct stat s;
int image, tail;
if (stat (argv[3], &s) < 0) die (argv[3]);
map = fopen (argv[2], "r");
if (!map) die(argv[2]);
while (fgets (buffer, 1024, map)) {
if (!strcmp (buffer + 19, "start\n"))
start = strtoul (buffer + 8, NULL, 16);
else if (!strcmp (buffer + 19, "end\n"))
end = strtoul (buffer + 8, NULL, 16);
}
fclose (map);
if ((image = open(argv[1],O_RDWR)) < 0) die(argv[1]);
if (read(image,buffer,512) != 512) die(argv[1]);
if (!memcmp (buffer, "\177ELF", 4)) {
unsigned int *p = (unsigned int *)(buffer + *(unsigned int *)(buffer + 28));
i = p[1] + *(unsigned int *)(buffer + 24) - p[2];
if (lseek(image,i,0) < 0) die("lseek");
if (read(image,buffer,512) != 512) die(argv[1]);
j = 0;
} else if (*(unsigned int *)buffer == 0x01030107) {
i = j = 32;
} else {
fprintf (stderr, "Not ELF nor a.out. Don't blame me.\n");
exit(1);
}
k = i;
if (j == 32 && buffer[40] == 'H' && buffer[41] == 'd' && buffer[42] == 'r' && buffer[43] == 'S') {
offset = 40 + 10;
} else {
i += ((*(unsigned short *)(buffer + j + 2))<<2) - 512;
if (lseek(image,i,0) < 0) die("lseek");
if (read(image,buffer,1024) != 1024) die(argv[1]);
for (q = buffer, r = q + 512; q < r; q += 4) {
if (*q == 'H' && q[1] == 'd' && q[2] == 'r' && q[3] == 'S')
break;
}
if (q == r) {
fprintf (stderr, "Couldn't find headers signature in the kernel.\n");
exit(1);
}
offset = i + (q - buffer) + 10;
}
if (lseek(image, offset, 0) < 0) die ("lseek");
*(unsigned *)buffer = 0;
*(unsigned *)(buffer + 4) = 0x01000000;
*(unsigned *)(buffer + 8) = ((end + 32 + 8191) & ~8191);
*(unsigned *)(buffer + 12) = s.st_size;
if (write(image,buffer+2,14) != 14) die (argv[1]);
if (lseek(image, 4, 0) < 0) die ("lseek");
*(unsigned *)buffer = ((end + 32 + 8191) & ~8191) - (start & ~0x3fffffUL) + s.st_size;
*(unsigned *)(buffer + 4) = 0;
*(unsigned *)(buffer + 8) = 0;
if (write(image,buffer,12) != 12) die (argv[1]);
if (lseek(image, k - start + ((end + 32 + 8191) & ~8191), 0) < 0) die ("lseek");
if ((tail = open(argv[3],O_RDONLY)) < 0) die(argv[3]);
while ((i = read (tail,buffer,1024)) > 0)
if (write(image,buffer,i) != i) die (argv[1]);
if (close(image) < 0) die("close");
if (close(tail) < 0) die("close");
return 0;
}
......@@ -94,7 +94,7 @@ CONFIG_INET=y
CONFIG_PATH_MTU_DISCOVERY=y
CONFIG_IP_NOSR=y
CONFIG_SKB_LARGE=y
# CONFIG_IPV6 is not set
CONFIG_IPV6=m
#
#
......@@ -120,7 +120,7 @@ CONFIG_SCSI=y
# SCSI support type (disk, tape, CDrom)
#
CONFIG_BLK_DEV_SD=y
# CONFIG_CHR_DEV_ST is not set
CONFIG_CHR_DEV_ST=y
CONFIG_BLK_DEV_SR=y
CONFIG_BLK_DEV_SR_VENDOR=y
CONFIG_CHR_DEV_SG=m
......@@ -141,13 +141,20 @@ CONFIG_SCSI_QLOGICPTI=m
# Network device support
#
CONFIG_NETDEVICES=y
CONFIG_DUMMY=y
# CONFIG_PPP is not set
# CONFIG_SLIP is not set
CONFIG_DUMMY=m
CONFIG_PPP=m
#
# CCP compressors for PPP are only built as modules.
#
CONFIG_SLIP=m
CONFIG_SLIP_COMPRESSED=y
CONFIG_SLIP_SMART=y
# CONFIG_SLIP_MODE_SLIP6 is not set
CONFIG_SUNLANCE=y
CONFIG_HAPPYMEAL=m
CONFIG_HAPPYMEAL=y
CONFIG_SUNQE=m
# CONFIG_MYRI_SBUS is not set
CONFIG_MYRI_SBUS=m
#
# Filesystems
......@@ -156,11 +163,11 @@ CONFIG_SUNQE=m
# CONFIG_DCACHE_PRELOAD is not set
# CONFIG_OMIRR is not set
# CONFIG_TRANS_NAMES is not set
# CONFIG_MINIX_FS is not set
CONFIG_MINIX_FS=m
CONFIG_EXT2_FS=y
# CONFIG_FAT_FS is not set
# CONFIG_MSDOS_FS is not set
# CONFIG_VFAT_FS is not set
CONFIG_FAT_FS=m
CONFIG_MSDOS_FS=m
CONFIG_VFAT_FS=m
# CONFIG_UMSDOS_FS is not set
CONFIG_PROC_FS=y
CONFIG_NFS_FS=y
......@@ -170,15 +177,17 @@ CONFIG_RNFS_BOOTP=y
CONFIG_NFSD=m
CONFIG_SUNRPC=y
CONFIG_LOCKD=y
# CONFIG_SMB_FS is not set
# CONFIG_NCP_FS is not set
CONFIG_SMB_FS=m
CONFIG_SMB_WIN95=y
CONFIG_NCP_FS=m
CONFIG_ISO9660_FS=y
# CONFIG_HPFS_FS is not set
# CONFIG_SYSV_FS is not set
# CONFIG_AFFS_FS is not set
# CONFIG_ROMFS_FS is not set
CONFIG_HPFS_FS=m
CONFIG_SYSV_FS=m
CONFIG_AFFS_FS=m
CONFIG_ROMFS_FS=m
CONFIG_AUTOFS_FS=m
CONFIG_UFS_FS=y
CONFIG_AMIGA_PARTITION=y
CONFIG_UFS_FS=m
CONFIG_BSD_DISKLABEL=y
CONFIG_SMD_DISKLABEL=y
......
......@@ -78,6 +78,7 @@ if (file.f_op->llseek) { \
static inline int
do_aout32_core_dump(long signr, struct pt_regs * regs)
{
struct dentry * dentry = NULL;
struct inode * inode = NULL;
struct file file;
unsigned short fs;
......@@ -103,10 +104,12 @@ do_aout32_core_dump(long signr, struct pt_regs * regs)
#else
corefile[4] = '\0';
#endif
if (open_namei(corefile,O_CREAT | 2 | O_TRUNC,0600,&inode,NULL)) {
inode = NULL;
dentry = open_namei(corefile,O_CREAT | 2 | O_TRUNC, 0600);
if (IS_ERR(dentry)) {
dentry = NULL;
goto end_coredump;
}
inode = dentry->d_inode;
if (!S_ISREG(inode->i_mode))
goto end_coredump;
if (!inode->i_op || !inode->i_op->default_file_ops)
......@@ -116,7 +119,7 @@ do_aout32_core_dump(long signr, struct pt_regs * regs)
file.f_mode = 3;
file.f_flags = 0;
file.f_count = 1;
file.f_inode = inode;
file.f_dentry = dentry;
file.f_pos = 0;
file.f_reada = 0;
file.f_op = inode->i_op->default_file_ops;
......@@ -169,7 +172,6 @@ do_aout32_core_dump(long signr, struct pt_regs * regs)
/* Finally dump the task struct. Not be used by gdb, but could be useful */
set_fs(KERNEL_DS);
DUMP_WRITE(current,sizeof(*current));
inode->i_status |= ST_MODIFIED;
close_coredump:
if (file.f_op->release)
file.f_op->release(inode,&file);
......@@ -177,7 +179,7 @@ do_aout32_core_dump(long signr, struct pt_regs * regs)
put_write_access(inode);
end_coredump:
set_fs(fs);
iput(inode);
dput(dentry);
return has_dumped;
}
......@@ -259,7 +261,7 @@ static inline int do_load_aout32_binary(struct linux_binprm * bprm,
if ((N_MAGIC(ex) != ZMAGIC && N_MAGIC(ex) != OMAGIC &&
N_MAGIC(ex) != QMAGIC && N_MAGIC(ex) != NMAGIC) ||
N_TRSIZE(ex) || N_DRSIZE(ex) ||
bprm->inode->i_size < ex.a_text+ex.a_data+N_SYMSIZE(ex)+N_TXTOFF(ex)) {
bprm->dentry->d_inode->i_size < ex.a_text+ex.a_data+N_SYMSIZE(ex)+N_TXTOFF(ex)) {
return -ENOEXEC;
}
......@@ -297,12 +299,12 @@ static inline int do_load_aout32_binary(struct linux_binprm * bprm,
error = do_mmap(NULL, N_TXTADDR(ex), ex.a_text,
PROT_READ|PROT_WRITE|PROT_EXEC,
MAP_FIXED|MAP_PRIVATE, 0);
read_exec(bprm->inode, fd_offset, (char *) N_TXTADDR(ex),
read_exec(bprm->dentry, fd_offset, (char *) N_TXTADDR(ex),
ex.a_text, 0);
error = do_mmap(NULL, N_DATADDR(ex), ex.a_data,
PROT_READ|PROT_WRITE|PROT_EXEC,
MAP_FIXED|MAP_PRIVATE, 0);
read_exec(bprm->inode, fd_offset + ex.a_text, (char *) N_DATADDR(ex),
read_exec(bprm->dentry, fd_offset + ex.a_text, (char *) N_DATADDR(ex),
ex.a_data, 0);
goto beyond_if;
}
......@@ -312,14 +314,14 @@ static inline int do_load_aout32_binary(struct linux_binprm * bprm,
ex.a_text+ex.a_data + PAGE_SIZE - 1,
PROT_READ|PROT_WRITE|PROT_EXEC,
MAP_FIXED|MAP_PRIVATE, 0);
read_exec(bprm->inode, fd_offset, (char *) N_TXTADDR(ex),
read_exec(bprm->dentry, fd_offset, (char *) N_TXTADDR(ex),
ex.a_text+ex.a_data, 0);
} else {
if ((ex.a_text & 0xfff || ex.a_data & 0xfff) &&
(N_MAGIC(ex) != NMAGIC))
printk(KERN_NOTICE "executable not page aligned\n");
fd = open_inode(bprm->inode, O_RDONLY);
fd = open_dentry(bprm->dentry, O_RDONLY);
if (fd < 0)
return fd;
......@@ -329,7 +331,7 @@ static inline int do_load_aout32_binary(struct linux_binprm * bprm,
do_mmap(NULL, 0, ex.a_text+ex.a_data,
PROT_READ|PROT_WRITE|PROT_EXEC,
MAP_FIXED|MAP_PRIVATE, 0);
read_exec(bprm->inode, fd_offset,
read_exec(bprm->dentry, fd_offset,
(char *) N_TXTADDR(ex), ex.a_text+ex.a_data, 0);
goto beyond_if;
}
......@@ -396,18 +398,21 @@ do_load_aout32_library(int fd)
{
struct file * file;
struct exec ex;
struct inode * inode;
struct dentry * dentry;
struct inode * inode;
unsigned int len;
unsigned int bss;
unsigned int start_addr;
unsigned long error;
file = current->files->fd[fd];
inode = file->f_inode;
if (!file || !file->f_op)
return -EACCES;
dentry = file->f_dentry;
inode = dentry->d_inode;
/* Seek into the file */
if (file->f_op->llseek) {
if ((error = file->f_op->llseek(inode, file, 0, 0)) != 0)
......
......@@ -28,6 +28,7 @@ struct cpu_fp_info {
*/
struct cpu_fp_info linux_sparc_fpu[] = {
{ 0x17, 0x10, 0, "UltraSparc I integrated FPU"},
{ 0x22, 0x10, 0, "UltraSparc II integrated FPU"},
{ 0x17, 0x11, 0, "UltraSparc II integrated FPU"},
{ 0x17, 0x12, 0, "UltraSparc III integrated FPU"},
};
......@@ -36,6 +37,7 @@ struct cpu_fp_info linux_sparc_fpu[] = {
struct cpu_iu_info linux_sparc_chips[] = {
{ 0x17, 0x10, "TI UltraSparc I (SpitFire)"},
{ 0x22, 0x10, "TI UltraSparc II (BlackBird)"},
{ 0x17, 0x11, "TI UltraSparc II (BlackBird)"},
{ 0x17, 0x12, "TI UltraSparc III (Cheetah)"}, /* A guess... */
};
......
/* $Id: entry.S,v 1.45 1997/07/05 09:52:25 davem Exp $
/* $Id: entry.S,v 1.50 1997/07/15 16:53:00 davem Exp $
* arch/sparc64/kernel/entry.S: Sparc64 trap low-level entry points.
*
* Copyright (C) 1995,1997 David S. Miller (davem@caip.rutgers.edu)
......@@ -7,6 +7,7 @@
* Copyright (C) 1996,1997 Jakub Jelinek (jj@sunsite.mff.cuni.cz)
*/
#include <linux/config.h>
#include <linux/errno.h>
#include <asm/head.h>
......@@ -191,16 +192,18 @@ fpdis_exit:
wrpr %g3, %tstate
retry
#ifdef __SMP__
/* Note check out head.h, this code isn't even used for UP,
* for SMP things will be different. In particular the data
* registers for cross calls will be:
*
* DATA 0: Address of function to call
* DATA 1: Argument 1, place in %g6
* DATA 2: Argument 2, place in %g7
* DATA 0: [low 32-bits] Address of function to call, jmp to this
* [high 32-bits] MMU Context Argument 0, place in %g5
* DATA 1: Address Argument 1, place in %g6
* DATA 2: Address Argument 2, place in %g7
*
* With this method we can do most of the cross-call tlb/cache
* flushing in very quickly.
* flushing very quickly.
*/
.align 32
.globl do_ivec
......@@ -211,12 +214,14 @@ do_ivec:
mov 0x40, %g2
/* Load up Interrupt Vector Data 0 register. */
sethi %hi(KERNBASE), %g4
ldxa [%g2] ASI_UDB_INTR_R, %g3
sethi %hi(ivector_to_mask), %g5
cmp %g3, %g4
bgeu,pn %xcc, do_ivec_xcall
nop
and %g3, 0x7ff, %g3
orcc %g5, %lo(ivector_to_mask), %g5
sllx %g3, 3, %g3
ldx [%g5 + %g3], %g2
ldx [%g1 + %g3], %g2
brz,pn %g2, do_ivec_spurious
nop
......@@ -231,7 +236,14 @@ do_ivec_return:
stxa %g0, [%g0] ASI_INTR_RECEIVE
membar #Sync
retry
do_ivec_xcall:
srlx %g3, 32, %g5
add %g2, 0x10, %g2
sra %g3, 0, %g3
ldxa [%g2] ASI_UDB_INTR_R, %g6
add %g2, 0x10, %g2
jmpl %g3, %g0
ldxa [%g2] ASI_UDB_INTR_R, %g7
do_ivec_spurious:
stxa %g0, [%g0] ASI_INTR_RECEIVE
membar #Sync
......@@ -243,6 +255,7 @@ do_ivec_spurious:
add %sp, STACK_BIAS + REGWIN_SZ, %o0
ba,pt %xcc, rtrap
clr %l6
#endif /* __SMP__ */
.globl getcc, setcc
getcc:
......@@ -263,10 +276,104 @@ setcc:
retl
stx %o1, [%o0 + PT_V9_TSTATE]
/* XXX Here is stuff we still need to write... -DaveM XXX */
.globl floppy_hardint, indirect_syscall, netbsd_syscall
.globl solaris_syscall
#ifdef CONFIG_BLK_DEV_FD
.globl floppy_hardint
floppy_hardint:
sethi %hi(doing_pdma), %g1
ld [%g1 + %lo(doing_pdma)], %g2
brz,pn %g2, floppy_dosoftint
sethi %hi(fdc_status), %g3
ldx [%g3 + %lo(fdc_status)], %g3
sethi %hi(pdma_vaddr), %g5
ldx [%g5 + %lo(pdma_vaddr)], %g4
sethi %hi(pdma_size), %g5
ldx [%g5 + %lo(pdma_size)], %g5
next_byte:
ldub [%g3], %g7
andcc %g7, 0x80, %g0
be,pn %icc, floppy_fifo_emptied
andcc %g7, 0x20, %g0
be,pn %icc, floppy_overrun
andcc %g7, 0x40, %g0
be,pn %icc, floppy_write
sub %g5, 1, %g5
ldub [%g3 + 1], %g7
orcc %g0, %g5, %g0
stb %g7, [%g4]
bne,pn %xcc, next_byte
add %g4, 1, %g4
b,pt %xcc, floppy_tdone
nop
floppy_write:
ldub [%g4], %g7
orcc %g0, %g5, %g0
stb %g7, [%g3 + 1]
bne,pn %xcc, next_byte
add %g4, 1, %g4
floppy_tdone:
sethi %hi(pdma_vaddr), %g1
stx %g4, [%g1 + %lo(pdma_vaddr)]
sethi %hi(pdma_size), %g1
stx %g5, [%g1 + %lo(pdma_size)]
sethi %hi(auxio_register), %g1
ldx [%g1 + %lo(auxio_register)], %g7
ldub [%g7], %g5
or %g5, 0xc2, %g5
stb %g5, [%g7]
andn %g5, 0x02, %g5
nop; nop; nop; nop; nop; nop;
nop; nop; nop; nop; nop; nop;
stb %g5, [%g7]
sethi %hi(doing_pdma), %g1
b,pt %xcc, floppy_dosoftint
st %g0, [%g1 + %lo(doing_pdma)]
floppy_fifo_emptied:
sethi %hi(pdma_vaddr), %g1
stx %g4, [%g1 + %lo(pdma_vaddr)]
sethi %hi(pdma_size), %g1
stx %g5, [%g1 + %lo(pdma_size)]
sethi %hi(irq_action), %g1
or %g1, %lo(irq_action), %g1
ldx [%g1 + (11 << 3)], %g3 ! irqaction[floppy_irq]
ldx [%g3 + 0x10], %g4 ! action->mask
st %g0, [%g4] ! SYSIO_ICLR_IDLE
membar #Sync ! probably not needed...
retry
floppy_overrun:
sethi %hi(pdma_vaddr), %g1
stx %g4, [%g1 + %lo(pdma_vaddr)]
sethi %hi(pdma_size), %g1
stx %g5, [%g1 + %lo(pdma_size)]
sethi %hi(doing_pdma), %g1
st %g0, [%g1 + %lo(doing_pdma)]
floppy_dosoftint:
rdpr %pil, %g2
wrpr %g0, 15, %pil
b,pt %xcc, etrap_irq
rd %pc, %g7
mov 11, %o0
mov 0, %o1
call sparc_floppy_irq
add %sp, STACK_BIAS + REGWIN_SZ, %o2
b,pt %xcc, rtrap
clr %l6
#endif /* CONFIG_BLK_DEV_FD */
/* XXX Here is stuff we still need to write... -DaveM XXX */
.globl indirect_syscall, netbsd_syscall, solaris_syscall
indirect_syscall:
netbsd_syscall:
solaris_syscall:
......@@ -436,16 +543,39 @@ sys_ptrace: call do_ptrace
ba,pt %xcc, rtrap
clr %l6
/* This is how fork() was meant to be done, 12 instruction entry. -DaveM */
.globl sys_fork, sys_vfork, sys_clone, ret_from_syscall
/* This is how fork() was meant to be done, 12 instruction entry.
*
* I questioned the following code briefly, let me clear things
* up so you must not reason on it like I did.
*
* Know the fork_kpsr etc. we use in the sparc32 port? We don't
* need it here because the only piece of window state we copy to
* the child is the CWP register. Even if the parent sleeps,
* we are safe because we stuck it into pt_regs of the parent
* so it will not change.
*
* XXX This raises the question, whether we can do the same on
* XXX sparc32 to get rid of fork_kpsr _and_ fork_kwim. The
* XXX answer is yes. We stick fork_kpsr in UREG_G0 and
* XXX fork_kwim in UREG_G1 (global registers are considered
* XXX volatile across a system call in the sparc ABI I think
* XXX if it isn't we can use regs->y instead, anyone who depends
* XXX upon the Y register being preserved across a fork deserves
* XXX to lose).
*
* In fact we should take advantage of that fact for other things
* during system calls...
*/
.globl sys_fork, sys_vfork, sys_clone
.globl ret_from_syscall, ret_from_smpfork
.align 32
sys_fork:
sys_vfork: mov SIGCHLD, %o0
clr %o1
sys_clone: mov %o7, %l5
save %sp, -REGWIN_SZ, %sp
/*???*/ save %sp, -REGWIN_SZ, %sp
flushw
restore %g0, %g0, %g0
/*???*/ restore %g0, %g0, %g0
rdpr %cwp, %o4
add %sp, STACK_BIAS + REGWIN_SZ, %o2
......@@ -453,10 +583,15 @@ sys_clone: mov %o7, %l5
stx %o4, [%sp + STACK_BIAS + REGWIN_SZ + PT_V9_G0]
call do_fork
mov %l5, %o7
ret_from_syscall:b,pt %xcc, ret_sys_call
ldx [%sp + STACK_BIAS + REGWIN_SZ + PT_V9_I0], %o0
nop
nop
#ifdef __SMP__
ret_from_smpfork:
sethi %hi(scheduler_lock), %o4
membar #StoreStore | #LoadStore
stb %g0, [%o4 + %lo(scheduler_lock)]
#endif
ret_from_syscall:
b,pt %xcc, ret_sys_call
ldx [%sp + STACK_BIAS + REGWIN_SZ + PT_V9_I0], %o0
linux_syscall_trace:
call syscall_trace
......
/* $Id: ioctl32.c,v 1.11 1997/06/16 11:05:00 jj Exp $
/* $Id: ioctl32.c,v 1.12 1997/07/09 15:05:28 davem Exp $
* ioctl32.c: Conversion between 32bit and 64bit native ioctls.
*
* Copyright (C) 1997 Jakub Jelinek (jj@sunsite.mff.cuni.cz)
......@@ -22,6 +22,7 @@
#include <linux/netlink.h>
#include <linux/vt.h>
#include <linux/fs.h>
#include <linux/fd.h>
#include <asm/types.h>
#include <asm/uaccess.h>
......@@ -485,8 +486,13 @@ asmlinkage int sys32_ioctl(unsigned int fd, unsigned int cmd, u32 arg)
int error = -EBADF;
lock_kernel();
if (fd >= NR_OPEN || !(filp = current->files->fd[fd]))
if(fd >= NR_OPEN)
goto out;
filp = current->files->fd[fd];
if(!filp)
goto out;
if (!filp->f_op || !filp->f_op->ioctl) {
error = sys_ioctl (fd, cmd, (unsigned long)arg);
goto out;
......@@ -612,6 +618,15 @@ asmlinkage int sys32_ioctl(unsigned int fd, unsigned int cmd, u32 arg)
case FIBMAP:
case FIGETBSZ:
/* 0x02 -- Floppy ioctls */
case FDSETEMSGTRESH:
case FDFLUSH:
case FDSETMAXERRS:
case FDGETMAXERRS:
case FDGETDRVTYP:
case FDEJECT:
/* XXX The rest need struct floppy_* translations. */
/* 0x12 */
case BLKRRPART:
case BLKFLSBUF:
......
/* $Id: irq.c,v 1.14 1997/06/24 17:30:26 davem Exp $
/* $Id: irq.c,v 1.16 1997/07/11 03:03:08 davem Exp $
* irq.c: UltraSparc IRQ handling/init/registry.
*
* Copyright (C) 1997 David S. Miller (davem@caip.rutgers.edu)
......@@ -47,7 +47,8 @@ unsigned long ivector_to_mask[NUM_IVECS];
static struct irqaction static_irqaction[MAX_STATIC_ALLOC];
static int static_irq_count = 0;
static struct irqaction *irq_action[NR_IRQS+1] = {
/* XXX Must be exported so that fast IRQ handlers can get at it... -DaveM */
struct irqaction *irq_action[NR_IRQS+1] = {
NULL, NULL, NULL, NULL, NULL, NULL , NULL, NULL,
NULL, NULL, NULL, NULL, NULL, NULL , NULL, NULL
};
......@@ -279,13 +280,13 @@ int request_irq(unsigned int irq, void (*handler)(int, void *, struct pt_regs *)
/* If this is flagged as statically allocated then we use our
* private struct which is never freed.
*/
if(irqflags & SA_STATIC_ALLOC)
if(irqflags & SA_STATIC_ALLOC) {
if(static_irq_count < MAX_STATIC_ALLOC)
action = &static_irqaction[static_irq_count++];
else
printk("Request for IRQ%d (%s) SA_STATIC_ALLOC failed "
"using kmalloc\n", irq, name);
}
if(action == NULL)
action = (struct irqaction *)kmalloc(sizeof(struct irqaction),
GFP_KERNEL);
......@@ -464,14 +465,101 @@ void sparc_floppy_irq(int irq, void *dev_cookie, struct pt_regs *regs)
}
#endif
/* XXX This needs to be written for floppy driver, and soon will be necessary
* XXX for serial driver as well.
/* The following assumes that the branch lies before the place we
* are branching to. This is the case for a trap vector...
* You have been warned.
*/
#define SPARC_BRANCH(dest_addr, inst_addr) \
(0x10800000 | ((((dest_addr)-(inst_addr))>>2)&0x3fffff))
#define SPARC_NOP (0x01000000)
static void install_fast_irq(unsigned int cpu_irq,
void (*handler)(int, void *, struct pt_regs *))
{
extern unsigned long sparc64_ttable_tl0;
unsigned long ttent = (unsigned long) &sparc64_ttable_tl0;
unsigned int *insns;
ttent += 0x820;
ttent += (cpu_irq - 1) << 5;
insns = (unsigned int *) ttent;
insns[0] = SPARC_BRANCH(((unsigned long) handler),
((unsigned long)&insns[0]));
insns[1] = SPARC_NOP;
__asm__ __volatile__("flush %0" : : "r" (ttent));
}
int request_fast_irq(unsigned int irq,
void (*handler)(int, void *, struct pt_regs *),
unsigned long irqflags, const char *name)
{
return -1;
struct irqaction *action;
unsigned long flags;
unsigned int cpu_irq, *imap, *iclr;
/* XXX This really is not the way to do it, the "right way"
* XXX is to have drivers set SA_SBUS or something like that
* XXX in irqflags and we base our decision here on whether
* XXX that flag bit is set or not.
*
* In this case nobody can have a fast interrupt at the level
* where TICK interrupts live.
*/
if(irq == 14)
return -EINVAL;
cpu_irq = ino_to_pil[irq];
if(!handler)
return -EINVAL;
imap = irq_to_imap(irq);
action = *(cpu_irq + irq_action);
if(action) {
if(action->flags & SA_SHIRQ)
panic("Trying to register fast irq when already shared.\n");
if(irqflags & SA_SHIRQ)
panic("Trying to register fast irq as shared.\n");
printk("request_fast_irq: Trying to register yet already owned.\n");
return -EBUSY;
}
save_and_cli(flags);
if(irqflags & SA_STATIC_ALLOC) {
if(static_irq_count < MAX_STATIC_ALLOC)
action = &static_irqaction[static_irq_count++];
else
printk("Request for IRQ%d (%s) SA_STATIC_ALLOC failed "
"using kmalloc\n", irq, name);
}
if(action == NULL)
action = (struct irqaction *)kmalloc(sizeof(struct irqaction),
GFP_KERNEL);
if(!action) {
restore_flags(flags);
return -ENOMEM;
}
install_fast_irq(cpu_irq, handler);
if(imap) {
int ivindex = (*imap & (SYSIO_IMAP_IGN | SYSIO_IMAP_INO));
ivector_to_mask[ivindex] = (1 << cpu_irq);
iclr = imap_to_iclr(imap);
action->mask = (unsigned long) iclr;
irqflags |= SA_SYSIO_MASKED;
} else
action->mask = 0;
action->handler = handler;
action->flags = irqflags;
action->dev_id = NULL;
action->name = name;
action->next = NULL;
*(cpu_irq + irq_action) = action;
enable_irq(irq);
restore_flags(flags);
return 0;
}
/* We really don't need these at all on the Sparc. We only have
......@@ -496,27 +584,31 @@ static unsigned long tick_offset;
/* XXX This doesn't belong here, just do this cruft in the timer.c handler code. */
static void timer_handler(int irq, void *dev_id, struct pt_regs *regs)
{
extern void timer_interrupt(int, void *, struct pt_regs *);
unsigned long compare;
if (!(get_softint () & 1)) {
/* Just to be sure... */
clear_softint(1 << 14);
printk("Spurious level14 at %016lx\n", regs->tpc);
return;
}
} else {
unsigned long compare, tick;
do {
extern void timer_interrupt(int, void *, struct pt_regs *);
timer_interrupt(irq, dev_id, regs);
timer_interrupt(irq, dev_id, regs);
/* Acknowledge INT_TIMER */
clear_softint(1 << 0);
/* Acknowledge INT_TIMER */
clear_softint(1 << 0);
/* Set up for next timer tick. */
__asm__ __volatile__("rd %%tick_cmpr, %0\n\t"
"add %0, %1, %0\n\t"
"wr %0, 0x0, %%tick_cmpr"
: "=r" (compare)
: "r" (tick_offset));
/* Set up for next timer tick. */
__asm__ __volatile__("rd %%tick_cmpr, %0\n\t"
"add %0, %2, %0\n\t"
"wr %0, 0x0, %%tick_cmpr\n\t"
"rd %%tick, %1"
: "=&r" (compare), "=r" (tick)
: "r" (tick_offset));
} while(tick >= compare);
}
}
/* This is called from time_init() to get the jiffies timer going. */
......@@ -584,7 +676,7 @@ static void map_prom_timers(void)
prom_timers = (struct sun5_timer *) 0;
return;
}
prom_timers = (struct sun5_timer *) addr[0];
prom_timers = (struct sun5_timer *) ((unsigned long)addr[0]);
}
static void kill_prom_timer(void)
......
/* $Id: process.c,v 1.26 1997/07/01 21:15:07 jj Exp $
/* $Id: process.c,v 1.28 1997/07/13 18:53:53 davem Exp $
* arch/sparc64/kernel/process.c
*
* Copyright (C) 1995, 1996 David S. Miller (davem@caip.rutgers.edu)
......@@ -17,6 +17,8 @@
#include <linux/sched.h>
#include <linux/kernel.h>
#include <linux/mm.h>
#include <linux/smp.h>
#include <linux/smp_lock.h>
#include <linux/stddef.h>
#include <linux/unistd.h>
#include <linux/ptrace.h>
......@@ -263,9 +265,6 @@ void show_stackframe32(struct sparc_stackf32 *sf)
void show_regs(struct pt_regs * regs)
{
#if __MPP__
printk("CID: %d\n",mpp_cid());
#endif
printk("TSTATE: %016lx TPC: %016lx TNPC: %016lx Y: %08x\n", regs->tstate,
regs->tpc, regs->tnpc, regs->y);
printk("g0: %016lx g1: %016lx g2: %016lx g3: %016lx\n",
......@@ -285,9 +284,6 @@ void show_regs(struct pt_regs * regs)
void show_regs32(struct pt_regs32 *regs)
{
#if __MPP__
printk("CID: %d\n",mpp_cid());
#endif
printk("PSR: %08x PC: %08x NPC: %08x Y: %08x\n", regs->psr,
regs->pc, regs->npc, regs->y);
printk("g0: %08x g1: %08x g2: %08x g3: %08x\n",
......@@ -365,26 +361,33 @@ void flush_thread(void)
__asm__ __volatile__("flush %g6");
}
static __inline__ struct sparc_stackf *
clone_stackframe(struct sparc_stackf *dst, struct sparc_stackf *src)
/* It's a bit more tricky when 64-bit tasks are involved... */
static unsigned long clone_stackframe(unsigned long csp, unsigned long psp)
{
struct sparc_stackf *sp;
#if 0
unsigned long size;
size = ((unsigned long)src->fp) - ((unsigned long)src);
sp = (struct sparc_stackf *)(((unsigned long)dst) - size);
if (copy_to_user(sp, src, size))
return 0;
if (put_user(dst, &sp->fp))
unsigned long fp, distance, rval;
if(!(current->tss.flags & SPARC_FLAG_32BIT)) {
csp += STACK_BIAS;
psp += STACK_BIAS;
__get_user(fp, &(((struct reg_window *)psp)->ins[6]));
} else
__get_user(fp, &(((struct reg_window32 *)psp)->ins[6]));
distance = fp - psp;
rval = (csp - distance);
if(copy_in_user(rval, psp, distance))
return 0;
#endif
return sp;
if(current->tss.flags & SPARC_FLAG_32BIT) {
if(put_user(((u32)csp), &(((struct reg_window32 *)rval)->ins[6])))
return 0;
return rval;
} else {
if(put_user(((u64)csp - STACK_BIAS),
&(((struct reg_window *)rval)->ins[6])))
return 0;
return rval - STACK_BIAS;
}
}
/* #define DEBUG_WINFIXUPS */
/* Standard stuff. */
static inline void shift_window_buffer(int first_win, int last_win,
struct thread_struct *tp)
......@@ -408,9 +411,6 @@ void synchronize_user_stack(void)
int winsize = REGWIN_SZ;
int bias = 0;
#ifdef DEBUG_WINFIXUPS
printk("sus(%d", (int)window);
#endif
if(tp->flags & SPARC_FLAG_32BIT)
winsize = REGWIN32_SZ;
else
......@@ -426,9 +426,6 @@ void synchronize_user_stack(void)
tp->w_saved--;
}
} while(window--);
#ifdef DEBUG_WINFIXUPS
printk(")");
#endif
}
}
......@@ -445,9 +442,6 @@ void fault_in_user_windows(struct pt_regs *regs)
bias = STACK_BIAS;
flush_user_windows();
window = tp->w_saved;
#ifdef DEBUG_WINFIXUPS
printk("fiuw(%d", (int)window);
#endif
if(window != 0) {
window -= 1;
do {
......@@ -459,9 +453,6 @@ void fault_in_user_windows(struct pt_regs *regs)
} while(window--);
}
current->tss.w_saved = 0;
#ifdef DEBUG_WINFIXUPS
printk(")");
#endif
}
/* Copy a Sparc thread. The fork() return value conventions
......@@ -485,10 +476,6 @@ int copy_thread(int nr, unsigned long clone_flags, unsigned long sp,
char *child_trap_frame;
int tframe_size;
#if 0 /* Now all syscall entries flip off the fpu. */
if(regs->tstate & TSTATE_PRIV)
regs->fprs = 0;
#endif
/* Calculate offset to stack_frame & pt_regs */
stack_offset = (((PAGE_SIZE << 1) -
((sizeof(unsigned int)*64) + (2*sizeof(unsigned long)))) &
......@@ -512,23 +499,14 @@ int copy_thread(int nr, unsigned long clone_flags, unsigned long sp,
p->tss.flags &= ~SPARC_FLAG_KTHREAD;
p->tss.current_ds = USER_DS;
p->tss.ctx = (p->mm->context & 0x1fff);
#if 0
if (sp != regs->u_regs[UREG_FP]) {
struct sparc_stackf *childstack;
struct sparc_stackf *parentstack;
/*
* This is a clone() call with supplied user stack.
* Set some valid stack frames to give to the child.
*/
childstack = (struct sparc_stackf *)sp;
parentstack = (struct sparc_stackf *)regs->u_regs[UREG_FP];
childstack = clone_stackframe(childstack, parentstack);
if (!childstack)
unsigned long csp;
csp = clone_stackframe(sp, regs->u_regs[UREG_FP]);
if(!csp)
return -EFAULT;
childregs->u_regs[UREG_FP] = (unsigned long)childstack;
p->tss.kregs->u_regs[UREG_FP] = csp;
}
#endif
}
/* Set the return value for the child. */
......@@ -592,9 +570,11 @@ asmlinkage int sparc_execve(struct pt_regs *regs)
if(regs->u_regs[UREG_G1] == 0)
base = 1;
error = getname((char *) regs->u_regs[base + UREG_I0], &filename);
if(error)
return error;
lock_kernel();
filename = getname((char *)regs->u_regs[base + UREG_I0]);
error = PTR_ERR(filename);
if(IS_ERR(filename))
goto out;
error = do_execve(filename, (char **) regs->u_regs[base + UREG_I1],
(char **) regs->u_regs[base + UREG_I2], regs);
putname(filename);
......@@ -602,5 +582,7 @@ asmlinkage int sparc_execve(struct pt_regs *regs)
fprs_write(0);
regs->fprs = 0;
}
out:
unlock_kernel();
return error;
}
......@@ -742,7 +742,7 @@ asmlinkage void do_ptrace(struct pt_regs *regs)
cregs->tstate |= psr_to_tstate_icc(psr);
if(!((pc | npc) & 3)) {
cregs->tpc = pc;
cregs->tpc = npc;
cregs->tnpc = npc;
}
cregs->y = y;
for(i = 1; i < 16; i++)
......
/* $Id: setup.c,v 1.9 1997/07/05 09:52:29 davem Exp $
/* $Id: setup.c,v 1.10 1997/07/08 11:07:47 jj Exp $
* linux/arch/sparc64/kernel/setup.c
*
* Copyright (C) 1995,1996 David S. Miller (davem@caip.rutgers.edu)
......@@ -35,6 +35,7 @@
#include <asm/page.h>
#include <asm/pgtable.h>
#include <asm/idprom.h>
#include <asm/head.h>
struct screen_info screen_info = {
0, 0, /* orig-x, orig-y */
......@@ -288,7 +289,7 @@ __initfunc(void setup_arch(char **cmdline_p,
*memory_start_p = PAGE_ALIGN(((unsigned long) &end));
*memory_end_p = (end_of_phys_memory + PAGE_OFFSET);
#ifndef NO_DAVEM_DEBUGGING
#ifdef DAVEM_DEBUGGING
prom_printf("phys_base[%016lx] memory_start[%016lx] memory_end[%016lx]\n",
phys_base, *memory_start_p, *memory_end_p);
#endif
......@@ -303,8 +304,11 @@ __initfunc(void setup_arch(char **cmdline_p,
#endif
#ifdef CONFIG_BLK_DEV_INITRD
if (ramdisk_image) {
initrd_start = ramdisk_image;
if (initrd_start < PAGE_OFFSET) initrd_start += PAGE_OFFSET;
unsigned long start = 0;
if (ramdisk_image >= (unsigned long)&end - 2 * PAGE_SIZE)
ramdisk_image -= KERNBASE;
initrd_start = ramdisk_image + phys_base + PAGE_OFFSET;
initrd_end = initrd_start + ramdisk_size;
if (initrd_end > *memory_end_p) {
printk(KERN_CRIT "initrd extends beyond end of memory "
......@@ -312,9 +316,11 @@ __initfunc(void setup_arch(char **cmdline_p,
initrd_end,*memory_end_p);
initrd_start = 0;
}
if (initrd_start >= *memory_start_p && initrd_start < *memory_start_p + 2 * PAGE_SIZE) {
if (initrd_start)
start = ramdisk_image + KERNBASE;
if (start >= *memory_start_p && start < *memory_start_p + 2 * PAGE_SIZE) {
initrd_below_start_ok = 1;
*memory_start_p = PAGE_ALIGN (initrd_end);
*memory_start_p = PAGE_ALIGN (start + ramdisk_size);
}
}
#endif
......
/* $Id: signal.c,v 1.17 1997/07/05 09:52:31 davem Exp $
/* $Id: signal.c,v 1.20 1997/07/14 03:10:28 davem Exp $
* arch/sparc64/kernel/signal.c
*
* Copyright (C) 1991, 1992 Linus Torvalds
......@@ -317,8 +317,6 @@ new_setup_frame(struct sigaction *sa, struct pt_regs *regs,
{
struct new_signal_frame *sf;
int sigframe_size;
unsigned long tmp;
int i;
/* 1. Make sure everything is clean */
synchronize_user_stack();
......@@ -329,16 +327,13 @@ new_setup_frame(struct sigaction *sa, struct pt_regs *regs,
sf = (struct new_signal_frame *)
(regs->u_regs[UREG_FP] + STACK_BIAS - sigframe_size);
if (invalid_frame_pointer (sf, sigframe_size)) {
lock_kernel ();
do_exit(SIGILL);
}
if (invalid_frame_pointer (sf, sigframe_size))
goto sigill;
if (current->tss.w_saved != 0) {
printk ("%s[%d]: Invalid user stack frame for "
"signal delivery.\n", current->comm, current->pid);
lock_kernel ();
do_exit (SIGILL);
goto sigill;
}
/* 2. Save the current process state */
......@@ -352,10 +347,10 @@ new_setup_frame(struct sigaction *sa, struct pt_regs *regs,
}
__put_user(oldmask, &sf->info.si_mask);
for (i = 0; i < sizeof(struct reg_window)/sizeof(u64); i++) {
__get_user(tmp, (((u64 *)(regs->u_regs[UREG_FP]+STACK_BIAS))+i));
__put_user(tmp, (((u64 *)sf)+i));
}
copy_in_user((u64 *)sf,
(u64 *)(regs->u_regs[UREG_FP]+STACK_BIAS),
sizeof(struct reg_window));
/* 3. return to kernel instructions */
__put_user(0x821020d8, &sf->insns[0]); /* mov __NR_sigreturn, %g1 */
......@@ -388,6 +383,11 @@ new_setup_frame(struct sigaction *sa, struct pt_regs *regs,
: "memory");
}
}
return;
sigill:
lock_kernel();
do_exit(SIGILL);
}
static inline void handle_signal(unsigned long signr, struct sigaction *sa,
......@@ -396,8 +396,11 @@ static inline void handle_signal(unsigned long signr, struct sigaction *sa,
new_setup_frame(sa, regs, signr, oldmask);
if(sa->sa_flags & SA_ONESHOT)
sa->sa_handler = NULL;
if(!(sa->sa_flags & SA_NOMASK))
if(!(sa->sa_flags & SA_NOMASK)) {
spin_lock_irq(&current->sigmask_lock);
current->blocked |= (sa->sa_mask | _S(signr)) & _BLOCKABLE;
spin_unlock_irq(&current->sigmask_lock);
}
}
static inline void syscall_restart(unsigned long orig_i0, struct pt_regs *regs,
......@@ -439,7 +442,11 @@ asmlinkage int do_signal(unsigned long oldmask, struct pt_regs * regs,
#endif
while ((signr = current->signal & mask) != 0) {
signr = ffz(~signr);
clear_bit(signr + 32, &current->signal);
spin_lock_irq(&current->sigmask_lock);
current->signal &= ~(1 << signr);
spin_unlock_irq(&current->sigmask_lock);
sa = current->sig->action + signr;
signr++;
if ((current->flags & PF_PTRACED) && signr != SIGKILL) {
......@@ -453,7 +460,9 @@ asmlinkage int do_signal(unsigned long oldmask, struct pt_regs * regs,
if (signr == SIGSTOP)
continue;
if (_S(signr) & current->blocked) {
spin_lock_irq(&current->sigmask_lock);
current->signal |= _S(signr);
spin_unlock_irq(&current->sigmask_lock);
continue;
}
sa = current->sig->action + signr - 1;
......@@ -496,8 +505,10 @@ asmlinkage int do_signal(unsigned long oldmask, struct pt_regs * regs,
case SIGQUIT: case SIGILL: case SIGTRAP:
case SIGABRT: case SIGFPE: case SIGSEGV: case SIGBUS:
if(current->binfmt && current->binfmt->core_dump) {
lock_kernel();
if(current->binfmt->core_dump(signr, regs))
signr |= 0x80;
unlock_kernel();
}
#ifdef DEBUG_SIGNALS
/* Very useful to debug dynamic linker problems */
......@@ -506,9 +517,15 @@ asmlinkage int do_signal(unsigned long oldmask, struct pt_regs * regs,
#endif
/* fall through */
default:
spin_lock_irq(&current->sigmask_lock);
current->signal |= _S(signr & 0x7f);
spin_unlock_irq(&current->sigmask_lock);
current->flags |= PF_SIGNALED;
lock_kernel();
do_exit(signr);
unlock_kernel();
}
}
if(restart_syscall)
......
/* $Id: signal32.c,v 1.23 1997/07/05 07:09:15 davem Exp $
/* $Id: signal32.c,v 1.26 1997/07/14 03:10:31 davem Exp $
* arch/sparc64/kernel/signal32.c
*
* Copyright (C) 1991, 1992 Linus Torvalds
......@@ -245,7 +245,6 @@ setup_frame32(struct sigaction *sa, unsigned long pc, unsigned long npc,
#endif
int old_status = current->tss.sstk_info.cur_status;
unsigned psr;
int i;
synchronize_user_stack();
regs->u_regs[UREG_FP] &= 0x00000000ffffffffUL;
......@@ -292,13 +291,9 @@ setup_frame32(struct sigaction *sa, unsigned long pc, unsigned long npc,
}
else
#endif
/* XXX Perhaps we need a copy_in_user()? -DaveM */
for (i = 0; i < 16; i++) {
u32 temp;
get_user (temp, (((u32 *)(regs->u_regs[UREG_FP]))+i));
put_user (temp, (((u32 *)sframep)+i));
}
copy_in_user((u32 *)sframep,
(u32 *)(regs->u_regs[UREG_FP]),
sizeof(struct reg_window32));
current->tss.w_saved = 0; /* So process is allowed to execute. */
__put_user(signr, &sframep->sig_num);
......@@ -351,8 +346,7 @@ static inline void new_setup_frame32(struct sigaction *sa, struct pt_regs *regs,
printk("new_setup_frame32(%s:%d): invalid_frame_pointer(%p, %d)\n",
current->comm, current->pid, sf, sigframe_size);
#endif
lock_kernel ();
do_exit(SIGILL);
goto sigill;
}
if (current->tss.w_saved != 0) {
......@@ -360,8 +354,7 @@ static inline void new_setup_frame32(struct sigaction *sa, struct pt_regs *regs,
printk ("%s[%d]: Invalid user stack frame for "
"signal delivery.\n", current->comm, current->pid);
#endif
lock_kernel ();
do_exit (SIGILL);
goto sigill;
}
/* 2. Save the current process state */
......@@ -384,13 +377,9 @@ static inline void new_setup_frame32(struct sigaction *sa, struct pt_regs *regs,
__put_user(oldmask, &sf->info.si_mask);
/* XXX Perhaps we need a copy_in_user()? -DaveM */
for (i = 0; i < sizeof(struct reg_window32)/4; i++) {
u32 tmp;
__get_user(tmp, (((u32 *)regs->u_regs[UREG_FP])+i));
__put_user(tmp, (((u32 *)sf)+i));
}
copy_in_user((u32 *)sf,
(u32 *)(regs->u_regs[UREG_FP]),
sizeof(struct reg_window32));
/* 3. return to kernel instructions */
__put_user(0x821020d8, &sf->insns[0]); /* mov __NR_sigreturn, %g1 */
......@@ -423,6 +412,11 @@ static inline void new_setup_frame32(struct sigaction *sa, struct pt_regs *regs,
: "memory");
}
}
return;
sigill:
lock_kernel();
do_exit(SIGILL);
}
/* Setup a Solaris stack frame */
......@@ -614,16 +608,16 @@ asmlinkage int svr4_setcontext32(svr4_ucontext_t *c, struct pt_regs *regs)
if (tp->w_saved){
printk ("Uh oh, w_saved is: 0x%lx\n", tp->w_saved);
do_exit(SIGSEGV);
goto sigsegv;
}
if (((unsigned long) c) & 3){
printk ("Unaligned structure passed\n");
do_exit (SIGSEGV);
goto sigsegv;
}
if(!__access_ok((unsigned long)c, sizeof(*c))) {
/* Miguel, add nice debugging msg _here_. ;-) */
do_exit(SIGSEGV);
goto sigsegv;
}
/* Check for valid PC and nPC */
......@@ -632,7 +626,7 @@ asmlinkage int svr4_setcontext32(svr4_ucontext_t *c, struct pt_regs *regs)
__get_user(npc, &((*gr)[SVR4_NPC]));
if((pc | npc) & 3) {
printk ("setcontext, PC or nPC were bogus\n");
do_exit (SIGSEGV);
goto sigsegv;
}
/* Retrieve information from passed ucontext */
/* note that nPC is ored a 1, this is used to inform entry.S */
......@@ -655,6 +649,9 @@ asmlinkage int svr4_setcontext32(svr4_ucontext_t *c, struct pt_regs *regs)
__get_user(regs->u_regs[UREG_I0+i], (&(*gr)[SVR4_O0])+i);
return -EINTR;
sigsegv:
lock_kernel();
do_exit(SIGSEGV);
}
static inline void handle_signal32(unsigned long signr, struct sigaction *sa,
......@@ -671,8 +668,11 @@ static inline void handle_signal32(unsigned long signr, struct sigaction *sa,
}
if(sa->sa_flags & SA_ONESHOT)
sa->sa_handler = NULL;
if(!(sa->sa_flags & SA_NOMASK))
if(!(sa->sa_flags & SA_NOMASK)) {
spin_lock_irq(&current->sigmask_lock);
current->blocked |= (sa->sa_mask | _S(signr)) & _BLOCKABLE;
spin_unlock_irq(&current->sigmask_lock);
}
}
static inline void syscall_restart32(unsigned long orig_i0, struct pt_regs *regs,
......@@ -708,7 +708,11 @@ asmlinkage int do_signal32(unsigned long oldmask, struct pt_regs * regs,
while ((signr = current->signal & mask) != 0) {
signr = ffz(~signr);
clear_bit(signr + 32, &current->signal);
spin_lock_irq(&current->sigmask_lock);
current->signal &= ~(1 << signr);
spin_unlock_irq(&current->sigmask_lock);
sa = current->sig->action + signr;
signr++;
if ((current->flags & PF_PTRACED) && signr != SIGKILL) {
......@@ -722,7 +726,9 @@ asmlinkage int do_signal32(unsigned long oldmask, struct pt_regs * regs,
if (signr == SIGSTOP)
continue;
if (_S(signr) & current->blocked) {
spin_lock_irq(&current->sigmask_lock);
current->signal |= _S(signr);
spin_unlock_irq(&current->sigmask_lock);
continue;
}
sa = current->sig->action + signr - 1;
......@@ -765,8 +771,10 @@ asmlinkage int do_signal32(unsigned long oldmask, struct pt_regs * regs,
case SIGQUIT: case SIGILL: case SIGTRAP:
case SIGABRT: case SIGFPE: case SIGSEGV: case SIGBUS:
if(current->binfmt && current->binfmt->core_dump) {
lock_kernel();
if(current->binfmt->core_dump(signr, regs))
signr |= 0x80;
unlock_kernel();
}
#ifdef DEBUG_SIGNALS
/* Very useful to debug dynamic linker problems */
......@@ -775,9 +783,15 @@ asmlinkage int do_signal32(unsigned long oldmask, struct pt_regs * regs,
#endif
/* fall through */
default:
spin_lock_irq(&current->sigmask_lock);
current->signal |= _S(signr & 0x7f);
spin_unlock_irq(&current->sigmask_lock);
current->flags |= PF_SIGNALED;
lock_kernel();
do_exit(signr);
unlock_kernel();
}
}
if(restart_syscall)
......
/* smp.c: Sparc64 SMP support.
*
* Copyright (C) 1997 David S. Miller (davem@caip.rutgers.edu)
*/
#define __KERNEL_SYSCALLS__
#include <linux/unistd.h>
extern int linux_num_cpus;
extern void calibrate_delay(void);
volatile int smp_processors_ready = 0;
unsigned long cpu_present_map = 0;
int smp_num_cpus = 1;
int smp_threads_ready = 0;
struct cpuinfo_sparc64 cpu_data[NR_CPUS];
static unsigned char boot_cpu_id = 0;
static int smp_activated = 0;
volatile int cpu_number_map[NR_CPUS];
volatile int cpu_logical_map[NR_CPUS];
struct klock_info klock_info = { KLOCK_CLEAR, 0 };
static volatile int smp_commenced = 0;
void smp_setup(char *str, int *ints)
{
/* XXX implement me XXX */
}
static char smp_buf[512];
char *smp_info(void)
{
/* XXX not SMP safe and need to support up to 64 penguins */
sprintf(smp_buf,
" CPU0\t\tCPU1\t\tCPU2\t\tCPU3\n"
"State: %s\t\t%s\t\t%s\t\t%s\n",
(cpu_present_map & 1) ? ((klock_info.akp == 0) ? "akp" : "online") : "offline",
(cpu_present_map & 2) ? ((klock_info.akp == 1) ? "akp" : "online") : "offline",
(cpu_present_map & 4) ? ((klock_info.akp == 2) ? "akp" : "online") : "offline",
(cpu_present_map & 8) ? ((klock_info.akp == 3) ? "akp" : "online") : "offline");
return smp_buf;
}
void smp_store_cpu_info(int id)
{
cpu_data[id].udelay_val = loops_per_sec;
}
void smp_commence(void)
{
local_flush_cache_all();
local_flush_tlb_all();
smp_commenced = 1;
local_flush_cache_all();
local_flush_tlb_all();
}
static void smp_setup_percpu_timer(void);
static volatile unsigned long callin_flag = 0;
void smp_callin(void)
{
int cpuid = hard_smp_processor_id();
local_flush_cache_all();
local_flush_tlb_all();
smp_setup_percpu_timer();
calibrate_delay();
smp_store_cpu_info(cpuid);
callin_flag = 1;
__asm__ __volatile__("membar #Sync\n\t"
"flush %g6" : : : "memory");
while(!task[cpuid])
barrier();
current = task[cpuid];
while(!smp_commenced)
barrier();
__sti();
}
extern int cpu_idle(void *unused);
extern void init_IRQ(void);
void initialize_secondary(void)
{
}
int start_secondary(void *unused)
{
trap_init();
init_IRQ();
smp_callin();
return cpu_idle(NULL);
}
extern struct prom_cpuinfo linux_cpus[NR_CPUS];
void smp_boot_cpus(void)
{
int cpucount = 0, i, first, prev;
printk("Entering UltraSMPenguin Mode...\n");
__sti();
cpu_present_map = 0;
for(i = 0; i < linux_num_cpus; i++)
cpu_present_map |= (1 << i);
for(i = 0; i < NR_CPUS; i++) {
cpu_number_map[i] = -1;
cpu_logical_map[i] = -1;
}
cpu_number_map[boot_cpu_id] = 0;
cpu_logical_map[0] = boot_cpu_id;
klock_info.akp = boot_cpu_id;
current->processor = boot_cpu_id;
smp_store_cpu_info(boot_cpu_id);
smp_setup_percpu_timer();
if(linux_num_cpus == 1)
return;
for(i = 0; i < NR_CPUS; i++) {
if(i == boot_cpu_id)
continue;
if(cpu_present_map & (1 << i)) {
extern unsigned long sparc64_cpu_startup;
unsigned long entry = (unsigned long)&sparc_cpu_startup;
struct task_struct *p;
int timeout;
kernel_thread(start_secondary, NULL, CLONE_PID);
p = task[++cpucount];
p->processor = i;
prom_startcpu(linux_cpus[i].prom_node, entry, i);
for(timeout = 0; timeout < 5000000; timeout++) {
if(cpu_callin_map[i])
break;
udelay(100);
}
if(cpu_callin_map[i]) {
/* XXX fix this */
cpu_number_map[i] = i;
cpu_logical_map[i] = i;
} else {
cpucount--;
printk("Processor %d is stuck.\n", i);
}
}
if(!(cpu_callin_map[i])) {
cpu_present_map &= ~(1 << i);
cpu_number_map[i] = -1;
}
}
if(cpucount == 0) {
printk("Error: only one processor found.\n");
cpu_present_map = (1 << smp_processor_id());
} else {
unsigned long bogosum = 0;
for(i = 0; i < NR_CPUS; i++) {
if(cpu_present_map & (1 << i))
bogosum += cpu_data[i].udelay_val;
}
printk("Total of %d processors activated (%lu.%02lu BogoMIPS).\n",
cpucount + 1,
(bogosum + 2500)/500000,
((bogosum + 2500)/5000)%100);
smp_activated = 1;
smp_num_cpus = cpucount + 1;
}
smp_processors_ready = 1;
}
/* XXX deprecated interface... */
void smp_message_pass(int target, int msg, unsigned long data, int wait)
{
printk("smp_message_pass() called, this is bad, spinning.\n");
__sti();
while(1)
barrier();
}
/* XXX Make it fast later. */
void smp_cross_call(unsigned long *func, u32 ctx, u64 data1, u64 data2)
{
if(smp_processors_ready) {
unsigned long mask;
u64 data0 = (((unsigned long)ctx)<<32 |
(((unsigned long)func) & 0xffffffff));
u64 pstate;
int i, ncpus = smp_num_cpus;
__asm__ __volatile__("rdpr %%pstate, %0" : "=r" (pstate));
mask = (cpu_present_map & ~(1 << smp_processor_id()));
for(i = 0; i < ncpus; i++) {
if(mask & (1 << i)) {
u64 target = mid<<14 | 0x70;
u64 result;
__asm__ __volatile__("
wrpr %0, %1, %%pstate
wrpr %%g0, %2, %%asi
stxa %3, [0x40] %%asi
stxa %4, [0x50] %%asi
stxa %5, [0x60] %%asi
stxa %%g0, [%6] %7
membar #Sync"
: /* No outputs */
: "r" (pstate), "i" (PSTATE_IE), "i" (ASI_UDB_INTR_W),
"r" (data0), "r" (data1), "r" (data2),
"r" (target), "i" (ASI_UDB_INTR_W));
/* NOTE: PSTATE_IE is still clear. */
do {
__asm__ __volatile__("ldxa [%%g0] %1, %0",
: "=r" (result)
: "i" (ASI_INTR_DISPATCH_STAT));
} while(result & 0x1);
__asm__ __volatile__("wrpr %0, 0x0, %%pstate"
: : "r" (pstate));
if(result & 0x2)
panic("Penguin NACK's master!");
}
}
/* NOTE: Caller runs local copy on master. */
}
}
extern unsigned long xcall_flush_tlb_page;
extern unsigned long xcall_flush_tlb_mm;
extern unsigned long xcall_flush_tlb_range;
extern unsigned long xcall_flush_tlb_all;
extern unsigned long xcall_flush_cache_all;
void smp_flush_cache_all(void)
{
smp_cross_call(&xcall_flush_cache_all, 0, 0, 0);
}
void smp_flush_tlb_all(void)
{
smp_cross_call(&xcall_flush_tlb_all, 0, 0, 0);
}
void smp_flush_tlb_mm(struct mm_struct *mm)
{
u32 ctx = mm->context & 0x1fff;
if(mm->cpu_vm_mask != (1 << smp_processor_id()))
smp_cross_call(&xcall_flush_tlb_mm, ctx, 0, 0);
__flush_tlb_mm(ctx);
}
void smp_flush_tlb_range(struct mm_struct *mm, unsigned long start,
unsigned long end)
{
u32 ctx = mm->context & 0x1fff;
if(mm->cpu_vm_mask != (1 << smp_processor_id()))
smp_cross_call(&xcall_flush_tlb_range, ctx, start, end);
__flush_tlb_range(ctx, start, end);
}
void smp_flush_tlb_page(struct vm_area_struct *vma, unsigned long page)
{
struct mm_struct *mm = vma->vm_mm;
u32 ctx = mm->context & 0x1fff;
if(mm->cpu_vm_mask != (1 << smp_processor_id()))
smp_cross_call(&xcall_flush_tlb_page, ctx, page, 0);
__flush_tlb_page(ctx, page);
}
static spinlock_t ticker_lock = SPIN_LOCK_UNLOCKED;
static inline void sparc64_do_profile(unsigned long pc)
{
if(prof_buffer && current->pid) {
extern int _stext;
pc -= (unsigned long) &_stext;
pc >>= prof_shift;
spin_lock(&ticker_lock);
if(pc < prof_len)
prof_buffer[pc]++;
else
prof_buffer[prof_len - 1]++;
spin_unlock(&ticker_lock);
}
}
unsigned int prof_multiplier[NR_CPUS];
unsigned int prof_counter[NR_CPUS];
extern void update_one_process(struct task_struct *p, unsigned long ticks,
unsigned long user, unsigned long system);
void smp_percpu_timer_interrupt(struct pt_regs *regs)
{
int cpu = smp_processor_id();
clear_profile_irq(cpu);
if(!user_mode(regs))
sparc_do_profile(regs->pc);
if(!--prof_counter[cpu]) {
int user = user_mode(regs);
if(current->pid) {
update_one_process(current, 1, user, !user);
if(--current->counter < 0) {
current->counter = 0;
need_resched = 1;
}
spin_lock(&ticker_lock);
if(user) {
if(current->priority < DEF_PRIORITY)
kstat.cpu_nice++;
else
kstat.cpu_user++;
} else {
kstat.cpu_system++;
}
spin_unlock(&ticker_lock);
}
prof_counter[cpu] = prof_multiplier[cpu];
}
}
static void smp_setup_percpu_timer(void)
{
/* XXX implement me */
}
int setup_profiling_timer(unsigned int multiplier)
{
/* XXX implement me */
}
/* $Id: sparc64_ksyms.c,v 1.8 1997/07/07 04:58:14 davem Exp $
/* $Id: sparc64_ksyms.c,v 1.11 1997/07/14 23:58:20 davem Exp $
* arch/sparc64/kernel/sparc64_ksyms.c: Sparc64 specific ksyms support.
*
* Copyright (C) 1996 David S. Miller (davem@caip.rutgers.edu)
......@@ -18,6 +18,8 @@
#include <asm/pgtable.h>
#include <asm/io.h>
#include <asm/irq.h>
#include <asm/softirq.h>
#include <asm/hardirq.h>
#include <asm/idprom.h>
#include <asm/svr4.h>
#include <asm/head.h>
......@@ -79,20 +81,12 @@ EXPORT_SYMBOL(mstk48t02_regs);
EXPORT_SYMBOL(request_fast_irq);
EXPORT_SYMBOL(sparc_alloc_io);
EXPORT_SYMBOL(sparc_free_io);
#if 0
EXPORT_SYMBOL(io_remap_page_range);
EXPORT_SYMBOL(mmu_unlockarea);
EXPORT_SYMBOL(mmu_lockarea);
EXPORT_SYMBOL(local_irq_count);
EXPORT_SYMBOL(__sparc64_bh_counter);
EXPORT_SYMBOL(sparc_ultra_unmapioaddr);
EXPORT_SYMBOL(mmu_get_scsi_sgl);
EXPORT_SYMBOL(mmu_get_scsi_one);
EXPORT_SYMBOL(mmu_release_scsi_sgl);
EXPORT_SYMBOL(mmu_release_scsi_one);
#endif
EXPORT_SYMBOL(sparc_dvma_malloc);
#if 0
EXPORT_SYMBOL(sun4c_unmapioaddr);
EXPORT_SYMBOL(srmmu_unmapioaddr);
#endif
#if CONFIG_SBUS
EXPORT_SYMBOL(SBus_chain);
EXPORT_SYMBOL(dma_chain);
......
/* $Id: sunos_ioctl32.c,v 1.2 1997/07/05 07:09:16 davem Exp $
/* $Id: sunos_ioctl32.c,v 1.3 1997/07/09 10:59:55 jj Exp $
* sunos_ioctl32.c: SunOS ioctl compatability on sparc64.
*
* Copyright (C) 1995 Miguel de Icaza (miguel@nuclecu.unam.mx)
......@@ -86,14 +86,19 @@ extern asmlinkage int sys_ioctl(unsigned int fd, unsigned int cmd, unsigned long
extern asmlinkage int sys32_ioctl(unsigned int, unsigned int, u32);
extern asmlinkage int sys_setsid(void);
asmlinkage int sunos_ioctl (int fd, unsigned long cmd, u32 arg)
asmlinkage int sunos_ioctl (int fd, u32 cmd, u32 arg)
{
struct file *filp;
int ret = -EBADF;
lock_kernel();
if(fd >= SUNOS_NR_OPEN || !(filp = current->files->fd[fd]))
if(fd >= SUNOS_NR_OPEN)
goto out;
filp = current->files->fd[fd];
if(!filp)
goto out;
if(cmd == TIOCSETD) {
unsigned long old_fs = get_fs();
int *p, ntty = N_TTY;
......
......@@ -759,14 +759,29 @@ static long do_readv_writev32(int type, struct inode *inode, struct file *file,
asmlinkage long sys32_readv(int fd, u32 vector, u32 count)
{
struct file *file;
struct dentry *dentry;
struct inode *inode;
long err = -EBADF;
lock_kernel();
if (fd >= NR_OPEN || !(file = current->files->fd[fd]) || !(inode=file->f_inode))
if(fd >= NR_OPEN)
goto out;
if (!(file->f_mode & 1))
file = current->files->fd[fd];
if(!file)
goto out;
if(!(file->f_mode & 1))
goto out;
dentry = file->f_dentry;
if(!dentry)
goto out;
inode = dentry->d_inode;
if(!inode)
goto out;
err = do_readv_writev32(VERIFY_WRITE, inode, file,
(struct iovec32 *)A(vector), count);
out:
......@@ -778,13 +793,28 @@ asmlinkage long sys32_writev(int fd, u32 vector, u32 count)
{
int error = -EBADF;
struct file *file;
struct dentry *dentry;
struct inode *inode;
lock_kernel();
if (fd >= NR_OPEN || !(file = current->files->fd[fd]) || !(inode=file->f_inode))
if(fd >= NR_OPEN)
goto out;
file = current->files->fd[fd];
if(!file)
goto out;
if(!(file->f_mode & 2))
goto out;
dentry = file->f_dentry;
if(!dentry)
goto out;
if (!(file->f_mode & 2))
inode = dentry->d_inode;
if(!inode)
goto out;
down(&inode->i_sem);
error = do_readv_writev32(VERIFY_READ, inode, file,
(struct iovec32 *)A(vector), count);
......@@ -833,21 +863,34 @@ asmlinkage int old32_readdir(unsigned int fd, u32 dirent, unsigned int count)
{
int error = -EBADF;
struct file * file;
struct dentry * dentry;
struct inode * inode;
struct readdir_callback32 buf;
lock_kernel();
if (fd >= NR_OPEN || !(file = current->files->fd[fd]))
if(fd >= NR_OPEN)
goto out;
error = -ENOTDIR;
if (!file->f_op || !file->f_op->readdir)
file = current->files->fd[fd];
if(!file)
goto out;
error = verify_area(VERIFY_WRITE, (void *)A(dirent),
sizeof(struct old_linux_dirent32));
if (error)
dentry = file->f_dentry;
if(!dentry)
goto out;
inode = dentry->d_inode;
if(!inode)
goto out;
buf.count = 0;
buf.dirent = (struct old_linux_dirent32 *)A(dirent);
error = file->f_op->readdir(file->f_inode, file, &buf, fillonedir);
error = -ENOTDIR;
if (!file->f_op || !file->f_op->readdir)
goto out;
error = file->f_op->readdir(inode, file, &buf, fillonedir);
if (error < 0)
goto out;
error = buf.count;
......@@ -897,30 +940,43 @@ static int filldir(void * __buf, const char * name, int namlen, off_t offset, in
asmlinkage int sys32_getdents(unsigned int fd, u32 dirent, unsigned int count)
{
struct file * file;
struct dentry * dentry;
struct inode *inode;
struct linux_dirent32 * lastdirent;
struct getdents_callback32 buf;
int error = -EBADF;
lock_kernel();
if (fd >= NR_OPEN || !(file = current->files->fd[fd]))
if(fd >= NR_OPEN)
goto out;
error = -ENOTDIR;
if (!file->f_op || !file->f_op->readdir)
file = current->files->fd[fd];
if(!file)
goto out;
error = verify_area(VERIFY_WRITE, (void *)A(dirent), count);
if (error)
dentry = file->f_dentry;
if(!dentry)
goto out;
inode = dentry->d_inode;
if(!inode)
goto out;
buf.current_dir = (struct linux_dirent32 *) A(dirent);
buf.previous = NULL;
buf.count = count;
buf.error = 0;
error = file->f_op->readdir(file->f_inode, file, &buf, filldir);
error = -ENOTDIR;
if (!file->f_op || !file->f_op->readdir)
goto out;
error = file->f_op->readdir(inode, file, &buf, filldir);
if (error < 0)
goto out;
lastdirent = buf.previous;
if (!lastdirent) {
error = buf.error;
} else {
error = buf.error;
if(lastdirent) {
put_user(file->f_pos, &lastdirent->d_off);
error = count - buf.count;
}
......@@ -1725,11 +1781,11 @@ extern __inline__ struct socket *sockfd_lookup(int fd, int *err)
return NULL;
}
inode = file->f_inode;
inode = file->f_dentry->d_inode;
if (!inode || !inode->i_sock || !socki_lookup(inode))
{
*err = -ENOTSOCK;
fput(file,inode);
fput(file);
return NULL;
}
......@@ -1738,7 +1794,7 @@ extern __inline__ struct socket *sockfd_lookup(int fd, int *err)
extern __inline__ void sockfd_put(struct socket *sock)
{
fput(sock->file,sock->inode);
fput(sock->file);
}
struct msghdr32 {
......@@ -2168,25 +2224,33 @@ static inline int
do_execve32(char * filename, u32 * argv, u32 * envp, struct pt_regs * regs)
{
struct linux_binprm bprm;
struct dentry * dentry;
int retval;
int i;
bprm.p = PAGE_SIZE*MAX_ARG_PAGES-sizeof(void *);
for (i=0 ; i<MAX_ARG_PAGES ; i++) /* clear page-table */
bprm.page[i] = 0;
retval = open_namei(filename, 0, 0, &bprm.inode, NULL);
if (retval)
dentry = open_namei(filename, 0, 0);
retval = PTR_ERR(dentry);
if (IS_ERR(dentry))
return retval;
bprm.dentry = dentry;
bprm.filename = filename;
bprm.sh_bang = 0;
bprm.java = 0;
bprm.loader = 0;
bprm.exec = 0;
bprm.dont_iput = 0;
if ((bprm.argc = count32(argv)) < 0)
if ((bprm.argc = count32(argv)) < 0) {
dput(dentry);
return bprm.argc;
if ((bprm.envc = count32(envp)) < 0)
}
if ((bprm.envc = count32(envp)) < 0) {
dput(dentry);
return bprm.envc;
}
retval = prepare_binprm(&bprm);
......@@ -2206,8 +2270,9 @@ do_execve32(char * filename, u32 * argv, u32 * envp, struct pt_regs * regs)
return retval;
/* Something went wrong, return the inode and free the argument pages*/
if(!bprm.dont_iput)
iput(bprm.inode);
if(bprm.dentry)
dput(bprm.dentry);
for (i=0 ; i<MAX_ARG_PAGES ; i++)
free_page(bprm.page[i]);
return(retval);
......@@ -2226,17 +2291,22 @@ asmlinkage int sparc32_execve(struct pt_regs *regs)
if((u32)regs->u_regs[UREG_G1] == 0)
base = 1;
error = getname((char *)(unsigned long)(u32)regs->u_regs[base + UREG_I0], &filename);
if(error)
return error;
lock_kernel();
filename = getname((char *)(unsigned long)(u32)regs->u_regs[base + UREG_I0]);
error = PTR_ERR(filename);
if(IS_ERR(filename))
goto out;
error = do_execve32(filename,
(u32 *)A((u32)regs->u_regs[base + UREG_I1]),
(u32 *)A((u32)regs->u_regs[base + UREG_I2]), regs);
putname(filename);
if(!error) {
fprs_write(0);
regs->fprs = 0;
}
out:
unlock_kernel();
return error;
}
......
......@@ -80,10 +80,12 @@ asmlinkage u32 sunos_mmap(u32 addr, u32 len, u32 prot, u32 flags, u32 fd, u32 of
goto out;
addr = (u32) attempt;
}
if(MAJOR(file->f_inode->i_rdev) == MEM_MAJOR &&
MINOR(file->f_inode->i_rdev) == 5) {
flags |= MAP_ANONYMOUS;
file = 0;
if(file->f_dentry && file->f_dentry->d_inode) {
if(MAJOR(file->f_dentry->d_inode->i_rdev) == MEM_MAJOR &&
MINOR(file->f_dentry->d_inode->i_rdev) == 5) {
flags |= MAP_ANONYMOUS;
file = 0;
}
}
if(!(flags & MAP_FIXED))
addr = 0;
......@@ -377,17 +379,33 @@ static int sunos_filldir(void * __buf, const char * name, int namlen,
asmlinkage int sunos_getdents(unsigned int fd, u32 u_dirent, int cnt)
{
struct file * file;
struct dentry * dentry;
struct inode * inode;
struct sunos_dirent * lastdirent;
struct sunos_dirent_callback buf;
int error = -EBADF;
void *dirent = (void *)A(u_dirent);
lock_kernel();
if (fd >= SUNOS_NR_OPEN || !(file = current->files->fd[fd]))
if(fd >= SUNOS_NR_OPEN)
goto out;
file = current->files->fd[fd];
if(!file)
goto out;
dentry = file->f_dentry;
if(!dentry)
goto out;
inode = dentry->d_inode;
if(!inode)
goto out;
error = -ENOTDIR;
if (!file->f_op || !file->f_op->readdir)
goto out;
error = -EINVAL;
if(cnt < (sizeof(struct sunos_dirent) + 255))
goto out;
......@@ -396,13 +414,13 @@ asmlinkage int sunos_getdents(unsigned int fd, u32 u_dirent, int cnt)
buf.previous = NULL;
buf.count = cnt;
buf.error = 0;
error = file->f_op->readdir(file->f_inode, file, &buf, sunos_filldir);
error = file->f_op->readdir(inode, file, &buf, sunos_filldir);
if (error < 0)
goto out;
lastdirent = buf.previous;
if (!lastdirent) {
error = buf.error;
} else {
error = buf.error;
if (lastdirent) {
put_user(file->f_pos, &lastdirent->d_off);
error = cnt - buf.count;
}
......@@ -454,6 +472,8 @@ asmlinkage int sunos_getdirentries(unsigned int fd, u32 u_dirent,
int cnt, u32 u_basep)
{
struct file * file;
struct dentry * dentry;
struct inode * inode;
struct sunos_direntry * lastdirent;
struct sunos_direntry_callback buf;
int error = -EBADF;
......@@ -461,11 +481,25 @@ asmlinkage int sunos_getdirentries(unsigned int fd, u32 u_dirent,
unsigned int *basep = (unsigned int *)A(u_basep);
lock_kernel();
if (fd >= SUNOS_NR_OPEN || !(file = current->files->fd[fd]))
if(fd >= SUNOS_NR_OPEN)
goto out;
file = current->files->fd[fd];
if(!file)
goto out;
dentry = file->f_dentry;
if(!dentry)
goto out;
inode = dentry->d_inode;
if(!inode)
goto out;
error = -ENOTDIR;
if (!file->f_op || !file->f_op->readdir)
goto out;
error = -EINVAL;
if(cnt < (sizeof(struct sunos_direntry) + 255))
goto out;
......@@ -474,13 +508,13 @@ asmlinkage int sunos_getdirentries(unsigned int fd, u32 u_dirent,
buf.previous = NULL;
buf.count = cnt;
buf.error = 0;
error = file->f_op->readdir(file->f_inode, file, &buf, sunos_filldirentry);
error = file->f_op->readdir(inode, file, &buf, sunos_filldirentry);
if (error < 0)
goto out;
lastdirent = buf.previous;
if (!lastdirent) {
error = buf.error;
} else {
error = buf.error;
if (lastdirent) {
put_user(file->f_pos, basep);
error = cnt - buf.count;
}
......@@ -684,12 +718,20 @@ sunos_nfs_get_server_fd (int fd, struct sockaddr_in *addr)
int try_port;
int ret;
struct socket *socket;
struct dentry *dentry;
struct inode *inode;
struct file *file;
file = current->files->fd [fd];
inode = file->f_inode;
if (!inode || !inode->i_sock)
if(!file)
return 0;
dentry = file->f_dentry;
if(!dentry)
return 0;
inode = dentry->d_inode;
if(!inode)
return 0;
socket = &inode->u.socket_i;
......@@ -770,7 +812,8 @@ asmlinkage int sunos_nfs_mount(char *dir_name, int linux_flags, void *data)
linux_nfs_mount.acdirmin = sunos_mount->acdirmin;
linux_nfs_mount.acdirmax = sunos_mount->acdirmax;
if (getname (sunos_mount->hostname, &the_name))
the_name = getname(sunos_mount->hostname);
if(IS_ERR(the_name))
return -EFAULT;
strncpy (linux_nfs_mount.hostname, the_name, 254);
......
/* $Id: winfixup.S,v 1.15 1997/07/04 01:41:07 davem Exp $
/* $Id: winfixup.S,v 1.16 1997/07/13 20:02:42 davem Exp $
*
* winfixup.S: Handle cases where user stack pointer is found to be bogus.
*
......@@ -68,7 +68,7 @@ fill_fixup:
mov %g5, %l5 ! Fault address
clr %l4 ! It was a load, not a store
wrpr %g0, 0x0, %tl ! Out of trap levels.
wrpr %l1, (PSTATE_IE | PSTATE_AG), %pstate
wrpr %l1, (PSTATE_IE | PSTATE_AG | PSTATE_RMO), %pstate
sethi %uhi(PAGE_OFFSET), %g4 ! Prepare page_offset global reg
mov %o7, %g6
b,pt %xcc, window_scheisse_merge ! And merge.
......@@ -186,7 +186,7 @@ fill_fixup_mna:
mov %g5, %o4 ! final call to do_sparc64_fault.
mov %g6, %o7 ! Stash away current.
wrpr %g0, 0x0, %tl ! Out of trap levels.
wrpr %l1, (PSTATE_IE | PSTATE_AG), %pstate
wrpr %l1, (PSTATE_IE | PSTATE_AG | PSTATE_RMO), %pstate
sethi %uhi(PAGE_OFFSET), %g4 ! Set page_offset global reg.
mov %o7, %g6 ! Get current back.
b,pt %xcc, window_mna_merge ! And merge.
......
/* $Id: VIScopy.S,v 1.8 1997/06/28 17:21:22 jj Exp $
/* $Id: VIScopy.S,v 1.9 1997/07/13 18:23:39 davem Exp $
* VIScopy.S: High speed copy operations utilizing the UltraSparc
* Visual Instruction Set.
*
......@@ -319,6 +319,14 @@ __copy_to_user: mov ASI_BLK_P, asi_src ! IEU0 Group
mov ASI_BLK_S, asi_dest ! IEU1
retl ! CTI Group
clr %o0 ! IEU0 Group
.globl __copy_in_user
.type __copy_in_user,@function
__copy_in_user: mov ASI_BLK_S, asi_src ! IEU0 Group
brnz,pt %o2, __memcpy_entry ! CTI
mov ASI_BLK_S, asi_dest ! IEU1
retl ! CTI Group
clr %o0 ! IEU0 Group
#endif
bcopy: or %o0, 0, %g3 ! IEU0 Group
......
......@@ -20,36 +20,27 @@ __strlen_user:
andcc %o0, 3, %g0
be,pt %icc, 9f
sethi %hi(HI_MAGIC), %o4
10:
lduba [%o0] ASI_S, %o5
10: lduba [%o0] ASI_S, %o5
brz,pn %o5, 21f
add %o0, 1, %o0
andcc %o0, 3, %g0
be,pn %icc, 4f
or %o4, %lo(HI_MAGIC), %o3
11:
lduba [%o0] ASI_S, %o5
11: lduba [%o0] ASI_S, %o5
brz,pn %o5, 22f
add %o0, 1, %o0
andcc %o0, 3, %g0
be,pt %icc, 5f
sethi %hi(LO_MAGIC), %o4
12:
lduba [%o0] ASI_S, %o5
be,pt %icc, 13f
srl %o3, 7, %o2
12: lduba [%o0] ASI_S, %o5
brz,pn %o5, 23f
add %o0, 1, %o0
ba,pt %icc, 13f
or %o4, %lo(LO_MAGIC), %o2
9:
or %o4, %lo(HI_MAGIC), %o3
4:
sethi %hi(LO_MAGIC), %o4
5:
or %o4, %lo(LO_MAGIC), %o2
13:
lda [%o0] ASI_S, %o5
2:
sub %o5, %o2, %o4
ba,pt %icc, 2f
15: lda [%o0] ASI_S, %o5
9: or %o4, %lo(HI_MAGIC), %o3
4: srl %o3, 7, %o2
13: lda [%o0] ASI_S, %o5
2: sub %o5, %o2, %o4
andcc %o4, %o3, %g0
be,pt %icc, 13b
add %o0, 4, %o0
......@@ -69,20 +60,15 @@ __strlen_user:
add %o4, 1, %o4
andcc %o5, 0xff, %g0
bne,a,pt %icc, 2b
14:
lda [%o0] ASI_S, %o5
14: lda [%o0] ASI_S, %o5
add %o4, 1, %o4
1:
retl
1: retl
sub %o4, %o1, %o0
21:
retl
21: retl
mov 1, %o0
22:
retl
22: retl
mov 2, %o0
23:
retl
23: retl
mov 3, %o0
.section .fixup,#alloc,#execinstr
......@@ -97,5 +83,6 @@ __strlen_user:
.xword 10b, 30b
.xword 11b, 30b
.xword 12b, 30b
.xword 15b, 30b
.xword 13b, 30b
.xword 14b, 30b
......@@ -228,7 +228,7 @@ void fixup_dcache_alias(struct vm_area_struct *vma, unsigned long address, pte_t
pte_t *ptep;
int alias_found = 0;
inode = vma->vm_inode;
inode = vma->vm_dentry->d_inode;
if(!inode)
return;
......
/* $Id: ultra.S,v 1.6 1997/06/30 10:31:43 jj Exp $
/* $Id: ultra.S,v 1.8 1997/07/15 05:35:50 davem Exp $
* ultra.S: Don't expand these all over the place...
*
* Copyright (C) 1997 David S. Miller (davem@caip.rutgers.edu)
......@@ -97,5 +97,130 @@ __flush_tlb_page: /* %o0 == (mm->context & 0x1fff), %o1 == page & PAGE_MASK */
retl
flush %g6
#ifdef __SMP__
/* These are all called by the slaves of a cross call, at
* trap level 1, with interrupts fully disabled.
*
* Register usage:
* %g5 mm->context (all tlb flushes)
* %g6 address arg 1 (tlb page and range flushes)
* %g7 address arg 2 (tlb range flush only)
*
* %g1 ivector table, don't touch
* %g2 scratch 1
* %g3 scratch 2
* %g4 scratch 3
*
* NOTE: We do not acknowledge the UPA until we are done
* with the service. This is what tells the master
* that he can consider the effects of the flush
* "complete" on this cpu.
*/
.align 32
.globl xcall_flush_tlb_page
xcall_flush_tlb_page:
mov SECONDARY_CONTEXT, %g2
nop
ldxa [%g2] ASI_DMMU, %g3
cmp %g3, %g5
be,pt %icc, 1f
or %g6, 0x10, %g4
stxa %g5, [%g2] ASI_DMMU
1: stxa %g0, [%g4] ASI_DMMU_DEMAP
be,pt %icc, 1f
stxa %g0, [%g4] ASI_IMMU_DEMAP
stxa %g3, [%g2] ASI_DMMU
1: b,pt %xcc, do_ivec_return
flush %g1
.align 32
.globl xcall_flush_tlb_mm
xcall_flush_tlb_mm:
mov SECONDARY_CONTEXT, %g2
nop
ldxa [%g2] ASI_DMMU, %g3
cmp %g3, %g5
be,pt %icc, 1f
mov 0x50, %g4
stxa %g5, [%g2] ASI_DMMU
1: stxa %g0, [%g4] ASI_DMMU_DEMAP
be,pt %icc, 1f
stxa %g0, [%g4] ASI_IMMU_DEMAP
stxa %g3, [%g2] ASI_DMMU
1: b,pt %xcc, do_ivec_return
flush %g1
.align 32
.globl xcall_flush_tlb_range
xcall_flush_tlb_range:
sethi %hi(8192 - 1), %g2
or %g2, %lo(8192 - 1), %g2
andn %g6, %g2, %g6
andn %g7, %g2, %g7
sub %g7, %g6, %g3
add %g2, 1, %g2
orcc %g6, 0x50, %g6
srlx %g3, 13, %g4
cmp %g4, 96
bgu,pn %icc, xcall_flush_tlb_mm
mov SECONDARY_CONTEXT, %g4
ldxa [%g4] ASI_DMMU, %g7
cmp %g7, %g5
be,pt %icc, 1f
sub %g3, %g2, %g3
stxa %g5, [%g4] ASI_DMMU
1: stxa %g0, [%g6 + %g3] ASI_DMMU_DEMAP
stxa %g0, [%g6 + %g3] ASI_IMMU_DEMAP
brnz,pt %g3, 1b
sub %g3, %g2, %g3
bne,a,pn %icc, 1f
stxa %g7, [%g4] ASI_DMMU
1: b,pt %xcc, do_ivec_return
flush %g1
/* These two are not performance critical... */
.globl xcall_flush_tlb_all
xcall_flush_tlb_all:
clr %g2
clr %g3
1: ldxa [%g3] ASI_DTLB_DATA_ACCESS, %g4
and %g4, _PAGE_L, %g5
brnz,pn %g5, 2f
mov TLB_TAG_ACCESS, %g7
stxa %g0, [%g7] ASI_DMMU
membar #Sync
stxa %g0, [%g3] ASI_DTLB_DATA_ACCESS
membar #Sync
2: ldxa [%g3] ASI_ITLB_DATA_ACCESS, %g4
and %g4, _PAGE_L, %g5
brnz,pn %g5, 2f
mov TLB_TAG_ACCESS, %g7
stxa %g0, [%g7] ASI_IMMU
membar #Sync
stxa %g0, [%g3] ASI_ITLB_DATA_ACCESS
2: add %g2, 1, %g2
cmp %g2, 63
ble,pt %icc, 1b
sll %g2, 3, %g3
b,pt %xcc, do_ivec_return
flush %g1
.globl xcall_flush_cache_all
xcall_flush_cache_all:
sethi %hi(16383), %g2
or %g2, %lo(16383), %g2
clr %g3
1: stxa %g0, [%g3] ASI_IC_TAG
add %g3, 32, %g3
cmp %g3, %g2
bleu,pt %xcc, 1b
nop
b,pt %xcc, do_ivec_return
flush %g1
#endif /* __SMP__ */
/* $Id: misc.c,v 1.7 1997/07/05 09:52:51 davem Exp $
/* $Id: misc.c,v 1.8 1997/07/14 23:45:28 davem Exp $
* misc.c: Miscellaneous prom functions that don't belong
* anywhere else.
*
......@@ -133,3 +133,10 @@ void prom_set_trap_table(unsigned long tba)
{
p1275_cmd("SUNW,set-trap-table", P1275_INOUT(1, 0), tba);
}
#ifdef __SMP__
void prom_start_cpu(int cpunode, unsigned long pc, unsigned long o0)
{
p1275_cmd("SUNW,start-cpu", P1275_INOUT(3, 0), cpunode, pc, o0);
}
#endif
......@@ -318,7 +318,7 @@ static int loop_set_fd(struct loop_device *lo, kdev_t dev, unsigned int arg)
}
lo->lo_inode = inode;
atomic_inc(&lo->lo_inode->i_count);
lo_inode->i_count++;
lo->transfer = NULL;
figure_loop_size(lo);
MOD_INC_USE_COUNT;
......
......@@ -202,10 +202,10 @@ static int do_md_stop (int minor, struct inode *inode)
{
int i;
if (atomic_read(&inode->i_count)>1 || md_dev[minor].busy>1) /* ioctl : one open channel */
if (inode->i_count > 1 || md_dev[minor].busy>1) /* ioctl : one open channel */
{
printk ("STOP_MD md%x failed : i_count=%d, busy=%d\n", minor,
atomic_read(&inode->i_count), md_dev[minor].busy);
inode->i_count, md_dev[minor].busy);
return -EBUSY;
}
......
......@@ -52,6 +52,7 @@ if [ "$CONFIG_MOUSE" = "y" ]; then
if [ "$CONFIG_PSMOUSE" != "n" ]; then
bool 'C&T 82C710 mouse port support (as on TI Travelmate)' CONFIG_82C710_MOUSE
fi
tristate 'PC110 digitizer pad support' CONFIG_PC110_PAD
fi
if [ "$CONFIG_MODULES" = "y" ]; then
......@@ -97,4 +98,5 @@ if [ "$CONFIG_WATCHDOG" != "n" ]; then
tristate ' Berkshire Products PC Watchdog' CONFIG_PCWATCHDOG
fi
bool 'Enhanced Real Time Clock Support' CONFIG_RTC
tristate 'PC joystick support' CONFIG_JOYSTICK
endmenu
......@@ -143,6 +143,14 @@ else
endif
endif
ifeq ($(CONFIG_JOYSTICK),y)
L_OBJS += joystick.o
else
ifeq ($(CONFIG_JOYSTICK),m)
M_OBJS += joystick.o
endif
endif
ifeq ($(CONFIG_MS_BUSMOUSE),y)
M = y
L_OBJS += msbusmouse.o
......@@ -212,6 +220,16 @@ ifdef CONFIG_SUN_MOUSE
M = y
endif
ifeq ($(CONFIG_PC110_PAD),y)
M = y
L_OBJS += pc110pad.o
else
ifeq ($(CONFIG_PC110_PAD),m)
M_OBJS += pc110pad.o
MM = m
endif
endif
ifeq ($(CONFIG_SUN_OPENPROMIO),y)
M = y
else
......
This diff is collapsed.
......@@ -724,7 +724,11 @@ __initfunc(int lp_init(void))
return 0;
printk(KERN_INFO "lp: driver loaded but no devices found\n");
#ifdef MODULE
return 0;
#else
return 1;
#endif
}
#ifdef MODULE
......
......@@ -20,6 +20,7 @@
#include <linux/mm.h>
#include <linux/random.h>
#include <linux/init.h>
#include <linux/joystick.h>
#include <asm/uaccess.h>
#include <asm/io.h>
......@@ -531,6 +532,13 @@ __initfunc(int chr_dev_init(void))
#ifdef CONFIG_SOUND
soundcard_init();
#endif
#ifdef CONFIG_JOYSTICK
/*
* Some joysticks only appear when the soundcard they are
* connected too is confgured. Keep the sound/joystick ordering.
*/
joystick_init();
#endif
#if CONFIG_QIC02_TAPE
qic02_tape_init();
#endif
......
......@@ -215,6 +215,9 @@ __initfunc(int misc_init(void))
#ifdef CONFIG_SUN_MOUSE
sun_mouse_init();
#endif
#ifdef CONFIG_PC110_PAD
pc110pad_init();
#endif
/*
* Only one watchdog can succeed. We probe the pcwatchdog first,
* then the wdt cards and finally the software watchdog which always
......
......@@ -706,7 +706,7 @@ static void n_tty_set_termios(struct tty_struct *tty, struct termios * old)
return;
tty->icanon = (L_ICANON(tty) != 0);
if (tty->flags & (1<<TTY_HW_COOK_IN)) {
if (test_bit(TTY_HW_COOK_IN, &tty->flags)) {
tty->raw = 1;
tty->real_raw = 1;
return;
......@@ -912,7 +912,7 @@ static int read_chan(struct tty_struct *tty, struct file *file,
tty->minimum_to_wake = (minimum - (b - buf));
if (!input_available_p(tty, 0)) {
if (tty->flags & (1 << TTY_OTHER_CLOSED)) {
if (test_bit(TTY_OTHER_CLOSED, &tty->flags)) {
retval = -EIO;
break;
}
......@@ -1030,7 +1030,7 @@ static int write_chan(struct tty_struct * tty, struct file * file,
retval = -EIO;
break;
}
if (O_OPOST(tty) && !(tty->flags & (1<<TTY_HW_COOK_OUT))) {
if (O_OPOST(tty) && !(test_bit(TTY_HW_COOK_OUT, &tty->flags))) {
while (nr > 0) {
num = opost_block(tty, b, nr);
b += num;
......@@ -1072,7 +1072,7 @@ static unsigned int normal_poll(struct tty_struct * tty, struct file * file, pol
mask |= POLLIN | POLLRDNORM;
if (tty->packet && tty->link->ctrl_status)
mask |= POLLPRI | POLLIN | POLLRDNORM;
if (tty->flags & (1 << TTY_OTHER_CLOSED))
if (test_bit(TTY_OTHER_CLOSED, &tty->flags))
mask |= POLLHUP;
if (tty_hung_up_p(file))
mask |= POLLHUP;
......
This diff is collapsed.
#ifndef _PC110PAD_H
#define _PC110PAD_H
#include <linux/ioctl.h>
enum pc110pad_mode {
PC110PAD_RAW, /* bytes as they come out of the hardware */
PC110PAD_RARE, /* debounced up/down and absolute x,y */
PC110PAD_DEBUG, /* up/down, debounced, transitions, button */
PC110PAD_PS2, /* ps2 relative (default) */
};
struct pc110pad_params {
enum pc110pad_mode mode;
int bounce_interval;
int tap_interval;
int irq;
int io;
};
#define MS *HZ/1000
/* Appears as device major=10 (MISC), minor=PC110_PAD */
#define PC110PAD_IOCTL_TYPE 0x9a
#define PC110PADIOCGETP _IOR(PC110PAD_IOCTL_TYPE, 0, struct pc110pad_params)
#define PC110PADIOCSETP _IOR(PC110PAD_IOCTL_TYPE, 1, struct pc110pad_params)
#endif /* _PC110PAD_H */
......@@ -180,7 +180,9 @@ static long rtc_read(struct inode *inode, struct file *file, char *buf,
data = rtc_irq_data;
rtc_irq_data = 0;
restore_flags(flags);
retval = put_user(data, (unsigned long *)buf) ?: sizeof(unsigned long);
retval = put_user(data, (unsigned long *)buf);
if (!retval)
retval = sizeof(unsigned long);
}
current->state = TASK_RUNNING;
......@@ -262,7 +264,6 @@ static int rtc_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
* "don't care" or "match all". Only the tm_hour,
* tm_min and tm_sec are used.
*/
int retval;
unsigned char hrs, min, sec;
struct rtc_time alm_tm;
......@@ -305,7 +306,6 @@ static int rtc_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
}
case RTC_SET_TIME: /* Set the RTC */
{
int retval;
struct rtc_time rtc_tm;
unsigned char mon, day, hrs, min, sec, leap_yr;
unsigned char save_control, save_freq_select;
......@@ -418,7 +418,7 @@ static int rtc_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
default:
return -EINVAL;
}
return copy_to_user(arg, &wtime, sizeof wtime) ? -EFAULT : 0;
return copy_to_user((void *)arg, &wtime, sizeof wtime) ? -EFAULT : 0;
}
/*
......
......@@ -389,7 +389,7 @@ void do_tty_hangup(struct tty_struct * tty, struct file_operations *fops)
tty->ldisc.flush_buffer(tty);
if (tty->driver.flush_buffer)
tty->driver.flush_buffer(tty);
if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
if ((test_bit(TTY_DO_WRITE_WAKEUP, &tty->flags)) &&
tty->ldisc.write_wakeup)
(tty->ldisc.write_wakeup)(tty);
wake_up_interruptible(&tty->write_wait);
......@@ -538,7 +538,7 @@ void start_tty(struct tty_struct *tty)
}
if (tty->driver.start)
(tty->driver.start)(tty);
if ((tty->flags & (1 << TTY_DO_WRITE_WAKEUP)) &&
if ((test_bit(TTY_DO_WRITE_WAKEUP, &tty->flags)) &&
tty->ldisc.write_wakeup)
(tty->ldisc.write_wakeup)(tty);
wake_up_interruptible(&tty->write_wait);
......@@ -553,7 +553,7 @@ static long tty_read(struct inode * inode, struct file * file,
tty = (struct tty_struct *)file->private_data;
if (tty_paranoia_check(tty, inode->i_rdev, "tty_read"))
return -EIO;
if (!tty || (tty->flags & (1 << TTY_IO_ERROR)))
if (!tty || (test_bit(TTY_IO_ERROR, &tty->flags)))
return -EIO;
/* This check not only needs to be done before reading, but also
......@@ -635,7 +635,7 @@ static long tty_write(struct inode * inode, struct file * file,
tty = (struct tty_struct *)file->private_data;
if (tty_paranoia_check(tty, inode->i_rdev, "tty_write"))
return -EIO;
if (!tty || !tty->driver.write || (tty->flags & (1 << TTY_IO_ERROR)))
if (!tty || !tty->driver.write || (test_bit(TTY_IO_ERROR, &tty->flags)))
return -EIO;
#if 0
if (!is_console && L_TOSTOP(tty) && (tty->pgrp > 0) &&
......@@ -824,7 +824,7 @@ static int init_dev(kdev_t device, struct tty_struct **ret_tty)
* opens on a pty master.
*/
fast_track:
if (tty->flags & (1 << TTY_CLOSING)) {
if (test_bit(TTY_CLOSING, &tty->flags)) {
retval = -EIO;
goto end_init;
}
......@@ -1071,9 +1071,9 @@ static void release_dev(struct file * filp)
* to close, and TTY_CLOSING makes sure we can't be reopened.
*/
if(tty_closing)
tty->flags |= (1 << TTY_CLOSING);
set_bit(TTY_CLOSING, &tty->flags);
if(o_tty_closing)
o_tty->flags |= (1 << TTY_CLOSING);
set_bit(TTY_CLOSING, &o_tty->flags);
/*
* If _either_ side is closing, make sure there aren't any
......
......@@ -84,6 +84,7 @@ if [ "$CONFIG_NET_ETHERNET" = "y" ]; then
tristate 'Digi Intl. RightSwitch SE-X support' CONFIG_DGRS
tristate 'EtherExpressPro/100 support' CONFIG_EEXPRESS_PRO100
if [ "$CONFIG_EXPERIMENTAL" = "y" ]; then
tristate 'TI ThunderLAN support (EXPERIMENTAL)' CONFIG_TLAN
tristate 'Racal-Interlan EISA ES3210 support (EXPERIMENTAL)' CONFIG_ES3210
bool 'Zenith Z-Note support (EXPERIMENTAL)' CONFIG_ZNET
fi
......@@ -151,12 +152,14 @@ if [ "$CONFIG_NET_RADIO" != "n" ]; then
bool 'Soundmodem support for 2400 baud AFSK modulation (8MHz crystal)' CONFIG_SOUNDMODEM_AFSK2400_8
bool 'Soundmodem support for 4800 baud HAPN-1 modulation' CONFIG_SOUNDMODEM_HAPN4800
bool 'Soundmodem support for 9600 baud FSK G3RUH modulation' CONFIG_SOUNDMODEM_FSK9600
if [ -f drivers/net/soundmodem/sm_afsk2666.c ]; then
bool 'Soundmodem support for 2666 baud AFSK modulation' CONFIG_SOUNDMODEM_AFSK2666
fi
if [ -f drivers/net/soundmodem/sm_psk4800.c ]; then
bool 'Soundmodem support for 4800 baud PSK modulation' CONFIG_SOUNDMODEM_PSK4800
fi
# if [ -f doesn't work with xconfig. Enable it again when the drivers are really
# included.
# if [ -f drivers/net/soundmodem/sm_afsk2666.c ]; then
# bool 'Soundmodem support for 2666 baud AFSK modulation' CONFIG_SOUNDMODEM_AFSK2666
# fi
# if [ -f drivers/net/soundmodem/sm_psk4800.c ]; then
# bool 'Soundmodem support for 4800 baud PSK modulation' CONFIG_SOUNDMODEM_PSK4800
# fi
fi
fi
tristate 'STRIP (Metricom starmode radio IP)' CONFIG_STRIP
......
......@@ -391,6 +391,14 @@ else
endif
endif
ifeq ($(CONFIG_TLAN),y)
L_OBJS += tlan.o
else
ifeq ($(CONFIG_TLAN),m)
M_OBJS += tlan.o
endif
endif
ifeq ($(CONFIG_ZNET),y)
L_OBJS += znet.o
endif
......@@ -793,7 +801,7 @@ dlci.o: dlci.c CONFIG
sdladrv.o: sdladrv.c CONFIG
wanpipe.o: $(WANPIPE_OBJS)
ld -r -o $@ $^
ld -r -o $@ $(WANPIPE_OBJS)
sdlamain.o: sdlamain.c CONFIG
......
------------------------------------------------------------------------------
WANPIPE(tm) Multiprotocol WAN Driver for Linux WAN Router
------------------------------------------------------------------------------
Release 3.0.0
December 31, 1996
Release 3.1.0
January 30, 1997
Author: Gene Kozin <genek@compuserve.com>
Copyright (c) 1995-1996 Sangoma Technologies Inc.
Copyright (c) 1995-1997 Sangoma Technologies Inc.
------------------------------------------------------------------------------
INTRODUCTION
......@@ -81,6 +81,12 @@ include/linux:
REVISION HISTORY
3.1.0 January 30, 1997
o Implemented IOCTL for executing adapter commands.
o Fixed a bug in frame relay code causing driver configured as a FR
switch to be stuck in WAN_DISCONNECTED mode.
3.0.0 December 31, 1996
o Uses Linux WAN Router interface
......
......@@ -89,6 +89,7 @@ extern int atarilance_probe(struct device *);
extern int a2065_probe(struct device *);
extern int ariadne_probe(struct device *);
extern int hydra_probe(struct device *);
extern int tlan_probe(struct device *);
extern int cs89x0_probe(struct device *dev);
/* Detachable devices ("pocket adaptors") */
......@@ -242,6 +243,9 @@ __initfunc(static int ethif_probe(struct device *dev))
#ifdef CONFIG_SUNLANCE
&& sparc_lance_probe(dev)
#endif
#ifdef CONFIG_TLAN
&& tlan_probe(dev)
#endif
#ifdef CONFIG_HAPPYMEAL
&& happy_meal_probe(dev)
#endif
......
......@@ -40,6 +40,7 @@ static const char *version =
* the driver figure it out.
*/
#include <linux/config.h>
#ifdef MODULE
#include <linux/module.h>
#include <linux/version.h>
......
......@@ -55,7 +55,10 @@
* + completed multiple adapter support. (November 20 1996)
* + implemented csum_partial_copy in tr_rx and increased receive
* buffer size and count. Minor fixes. (March 15, 1997)
*/
*
* Changes by Christopher Turcksin <wabbit@rtfc.demon.co.uk>
* + Now compiles ok as a module again.
*/
#ifdef PCMCIA
#define MODULE
......@@ -163,9 +166,9 @@ unsigned char ibmtr_debug_trace=0;
int ibmtr_probe(struct device *dev);
static int ibmtr_probe1(struct device *dev, int ioaddr);
unsigned char get_sram_size(struct tok_info *adapt_info);
static unsigned char get_sram_size(struct tok_info *adapt_info);
static int tok_init_card(struct device *dev);
int trdev_init(struct device *dev);
static int trdev_init(struct device *dev);
void tok_interrupt(int irq, void *dev_id, struct pt_regs *regs);
static void initial_tok_int(struct device *dev);
static void open_sap(unsigned char type,struct device *dev);
......@@ -1583,7 +1586,7 @@ int init_module(void)
dev_ibmtr[i]->init = &ibmtr_probe;
if (register_trdev(dev_ibmtr[i]) != 0) {
kfree_s(dev_ibmtr[i], sizeof(struct dev));
kfree_s(dev_ibmtr[i], sizeof(struct device));
dev_ibmtr[i] = NULL;
if (i == 0) {
printk("ibmtr: register_trdev() returned non-zero.\n");
......
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment