Commit 4cb8ac91 authored by Linus Torvalds's avatar Linus Torvalds

Import 2.0.17

parent 6d58893f
......@@ -1104,7 +1104,7 @@ interface. PD is the Motorola Public Domain Interface and ICD is the
commercial interface by P\&E.
\begin{devicelist}
\major{54}{Electrocardiognosis Holter serial card}
\major{54}{}{char }{Electrocardiognosis Holter serial card}
\minor{0}{/dev/holter0}{First Holter port}
\minor{1}{/dev/holter1}{Second Holter port}
\minor{2}{/dev/holter2}{Third Holter port}
......
VERSION = 2
PATCHLEVEL = 0
SUBLEVEL = 16
SUBLEVEL = 17
ARCH = i386
......
/*
* linux/drivers/block/cmd640.c Version 1.01 Aug 12, 1996
* linux/drivers/block/cmd640.c Version 1.02 Sep 01, 1996
*
* Copyright (C) 1995-1996 Linus Torvalds & authors (see below)
*/
......@@ -94,9 +94,12 @@
* Version 1.00 Mmm.. cannot depend on PCMD_ENA in all systems
* Version 1.01 slow/fast devsel can be selected with "hdparm -p6/-p7"
* ("fast" is necessary for 32bit I/O in some systems)
* Version 1.02 fix bug that resulted in slow "setup times"
* (patch courtesy of Zoltan Hidvegi)
*/
#undef REALLY_SLOW_IO /* most systems can safely undef this */
#define CMD640_PREFETCH_MASKS 1
#include <linux/config.h>
#include <linux/types.h>
......@@ -408,9 +411,11 @@ static void check_prefetch (unsigned int index)
drive->no_io_32bit = 1;
drive->io_32bit = 0;
} else {
#if CMD640_PREFETCH_MASKS
drive->no_unmask = 1;
drive->no_io_32bit = 0;
drive->unmask = 0;
#endif
drive->no_io_32bit = 0;
}
}
......@@ -454,8 +459,10 @@ static void set_prefetch_mode (unsigned int index, int mode)
cli();
b = get_cmd640_reg(reg);
if (mode) { /* want prefetch on? */
#if CMD640_PREFETCH_MASKS
drive->no_unmask = 1;
drive->unmask = 0;
#endif
drive->no_io_32bit = 0;
b &= ~prefetch_masks[index]; /* enable prefetch */
} else {
......@@ -556,9 +563,10 @@ static void program_drive_counts (unsigned int index)
* Convert setup_count to internal chipset representation
*/
switch (setup_count) {
case 4: setup_count = 0x00;
case 3: setup_count = 0x80;
case 2: setup_count = 0x40;
case 4: setup_count = 0x00; break;
case 3: setup_count = 0x80; break;
case 1:
case 2: setup_count = 0x40; break;
default: setup_count = 0xc0; /* case 5 */
}
......
......@@ -4067,12 +4067,16 @@ static int floppy_grab_irq_and_dma(void)
if (fd_request_irq()) {
DPRINT("Unable to grab IRQ%d for the floppy driver\n",
FLOPPY_IRQ);
MOD_DEC_USE_COUNT;
usage_count--;
return -1;
}
if (fd_request_dma()) {
DPRINT("Unable to grab DMA%d for the floppy driver\n",
FLOPPY_DMA);
fd_free_irq();
MOD_DEC_USE_COUNT;
usage_count--;
return -1;
}
for (fdc = 0; fdc < N_FDC; fdc++)
......@@ -4098,7 +4102,6 @@ static void floppy_release_irq_and_dma(void)
return;
}
INT_ON;
MOD_DEC_USE_COUNT;
fd_disable_dma();
fd_free_dma();
fd_disable_irq();
......@@ -4131,6 +4134,7 @@ static void floppy_release_irq_and_dma(void)
if (floppy_tq.sync)
printk("task queue still active\n");
#endif
MOD_DEC_USE_COUNT;
}
......
This diff is collapsed.
......@@ -1433,34 +1433,34 @@ static int con_write(struct tty_struct * tty, int from_user,
tc = translate[toggle_meta ? (c|0x80) : c];
}
/* If the original code was < 32 we only allow a
* glyph to be displayed if the code is not normally
* used (such as for cursor movement) or if the
* disp_ctrl mode has been explicitly enabled.
* Note: ESC is *never* allowed to be displayed as
* that would disable all escape sequences!
* To display font position 0x1B, go into UTF mode
* and display character U+F01B, or change the mapping.
*/
ok = (tc && (c >= 32 || (!utf && !(((disp_ctrl ? CTRL_ALWAYS
: CTRL_ACTION) >> c) & 1))));
/* If the original code was a control character we
* only allow a glyph to be displayed if the code is
* not normally used (such as for cursor movement) or
* if the disp_ctrl mode has been explicitly enabled.
* Certain characters (as given by the CTRL_ALWAYS
* bitmap) are always displayed as control characters,
* as the console would be pretty useless without
* them; to display an arbitrary font position use the
* direct-to-font zone in UTF-8 mode.
*/
ok = tc && (c >= 32 ||
(!utf && !(((disp_ctrl ? CTRL_ALWAYS
: CTRL_ACTION) >> c) & 1)))
&& (c != 127 || disp_ctrl);
if (vc_state == ESnormal && ok) {
/* Now try to find out how to display it */
tc = conv_uni_to_pc(tc);
if ( tc == -4 )
{
/* If we got -4 (not found) then see if we have
defined a replacement character (U+FFFD) */
tc = conv_uni_to_pc(0xfffd);
}
else if ( tc == -3 )
{
/* Bad hash table -- hope for the best */
tc = c;
}
if ( tc == -4 ) {
/* If we got -4 (not found) then see if we have
defined a replacement character (U+FFFD) */
tc = conv_uni_to_pc(0xfffd);
} else if ( tc == -3 ) {
/* Bad hash table -- hope for the best */
tc = c;
}
if (tc & ~console_charmask)
continue; /* Conversion failed */
continue; /* Conversion failed */
if (need_wrap) {
cr(currcons);
......
......@@ -311,7 +311,7 @@ int fdc_interrupt_wait(int time)
int current_blocked = current->blocked;
static int resetting = 0;
if (wait_intr) {
if (waitqueue_active(&wait_intr)) {
TRACE(1, "error: nested call");
return -EIO; /* return error... */
}
......
......@@ -771,7 +771,7 @@ fdc_isr(void)
}
seek_completed = 1;
fdc_mode = fdc_idle;
} else if (!wait_intr) {
} else if (!waitqueue_active(&wait_intr)) {
if (expected_stray_interrupts == 0) {
TRACE(2, "unexpected stray interrupt");
} else {
......
......@@ -795,7 +795,7 @@ static int read_chan(struct tty_struct *tty, struct file *file,
current->timeout = (unsigned long) -1;
if (time)
tty->minimum_to_wake = 1;
else if (!tty->read_wait ||
else if (!waitqueue_active(&tty->read_wait) ||
(tty->minimum_to_wake > minimum))
tty->minimum_to_wake = minimum;
} else {
......@@ -907,7 +907,7 @@ static int read_chan(struct tty_struct *tty, struct file *file,
}
remove_wait_queue(&tty->read_wait, &wait);
if (!tty->read_wait)
if (!waitqueue_active(&tty->read_wait))
tty->minimum_to_wake = minimum;
current->state = TASK_RUNNING;
......@@ -991,7 +991,7 @@ static int normal_select(struct tty_struct * tty, struct inode * inode,
return 1;
if (tty_hung_up_p(file))
return 1;
if (!tty->read_wait) {
if (!waitqueue_active(&tty->read_wait)) {
if (MIN_CHAR(tty) && !TIME_CHAR(tty))
tty->minimum_to_wake = MIN_CHAR(tty);
else
......
......@@ -1349,7 +1349,7 @@ static int tty_fasync(struct inode * inode, struct file * filp, int on)
return retval;
if (on) {
if (!tty->read_wait)
if (!waitqueue_active(&tty->read_wait))
tty->minimum_to_wake = 1;
if (filp->f_owner == 0) {
if (tty->pgrp)
......@@ -1358,7 +1358,7 @@ static int tty_fasync(struct inode * inode, struct file * filp, int on)
filp->f_owner = current->pid;
}
} else {
if (!tty->fasync && !tty->read_wait)
if (!tty->fasync && !waitqueue_active(&tty->read_wait))
tty->minimum_to_wake = N_TTY_BUF_SIZE;
}
return 0;
......
......@@ -90,7 +90,7 @@ extern void enable_irq(unsigned int);
"outb %al,$0x21\n\t" \
"jmp 1f\n" \
"1:\tjmp 1f\n" \
"1:\tmovb $0x60+"#nr",%al\n\t" \
"1:\tmovb $0xE0+"#nr",%al\n\t" \
"outb %al,$0x20\n\t"
#define ACK_SECOND(mask,nr) \
......@@ -102,11 +102,11 @@ extern void enable_irq(unsigned int);
"outb %al,$0xA1\n\t" \
"jmp 1f\n" \
"1:\tjmp 1f\n" \
"1:\tmovb $0x60+"#nr",%al\n\t" \
"1:\tmovb $0xE0+"#nr",%al\n\t" \
"outb %al,$0xA0\n\t" \
"jmp 1f\n" \
"1:\tjmp 1f\n" \
"1:\tmovb $0x62,%al\n\t" \
"1:\tmovb $0xE2,%al\n\t" \
"outb %al,$0x20\n\t"
#define UNBLK_FIRST(mask) \
......
......@@ -134,16 +134,38 @@
/* runtime by use of the CDROMAUDIOBUFSIZ ioctl. */
#define READ_AUDIO 0
/* Optimizations for the Teac CD-55A drive read performance.
* SBP_TEAC_SPEED can be changed here, or one can set the
* variable "teac" when loading as a module.
* Valid settings are:
* 0 - very slow - the recommended "DISTRIBUTION 1" setup.
* 1 - 2x performance with little overhead. No busy waiting.
* 2 - 4x performance with 5ms overhead per read. Busy wait.
*
* Setting SBP_TEAC_SPEED or the variable 'teac' to anything
* other than 0 may cause problems. If you run into them, first
* change SBP_TEAC_SPEED back to 0 and see if your drive responds
* normally. If yes, you are "allowed" to report your case - to help
* me with the driver, not to solve your hassle. Dont mail if you
* simply are stuck into your own "tuning" experiments, you know?
*/
#define SBP_TEAC_SPEED 1
/*==========================================================================*/
/*==========================================================================*/
/*
* nothing to change below here if you are not experimenting
* nothing to change below here if you are not fully aware what you're doing
*/
#ifndef _LINUX_SBPCD_H
#define _LINUX_SBPCD_H
/*==========================================================================*/
/*==========================================================================*/
/*
* driver's own read_ahead, data mode
*/
#define SBP_BUFFER_FRAMES 8
#define LONG_TIMING 0 /* test against timeouts with "gold" CDs on CR-521 */
#undef FUTURE
#undef SAFE_MIXED
......@@ -151,10 +173,15 @@
#define TEST_UPC 0
#define SPEA_TEST 0
#define TEST_STI 0
#define OLD_BUSY 0
#undef PATH_CHECK
#ifndef SOUND_BASE
#define SOUND_BASE 0
#endif
#if DISTRIBUTION
#undef SBP_TEAC_SPEED
#define SBP_TEAC_SPEED 0
#endif
/*==========================================================================*/
/*
* DDI interface definitions
......
......@@ -260,8 +260,8 @@ struct task_struct {
#define PF_DUMPCORE 0x00000200 /* dumped core */
#define PF_SIGNALED 0x00000400 /* killed by a signal */
#define PF_STARTING 0x00000100 /* being created */
#define PF_EXITING 0x00000200 /* getting shut down */
#define PF_STARTING 0x00000002 /* being created */
#define PF_EXITING 0x00000004 /* getting shut down */
#define PF_USEDFPU 0x00100000 /* Process used the FPU this quantum (SMP only) */
#define PF_DTRACE 0x00200000 /* delayed trace (used on m68k) */
......
......@@ -161,6 +161,7 @@ extern void tcp_send_reset(unsigned long saddr, unsigned long daddr, struct tcph
extern void tcp_enqueue_partial(struct sk_buff *, struct sock *);
extern struct sk_buff * tcp_dequeue_partial(struct sock *);
extern void tcp_shrink_skb(struct sock *,struct sk_buff *,u32);
/* tcp_input.c */
extern void tcp_cache_zap(void);
......
......@@ -978,10 +978,11 @@ static int tcp_ack(struct sock *sk, struct tcphdr *th, u32 ack, int len)
/*
* Maybe we can take some stuff off of the write queue,
* and put it onto the xmit queue.
* FIXME: (?) There is bizarre case being tested here, to check if
* There is bizarre case being tested here, to check if
* the data at the head of the queue ends before the start of
* the sequence we already ACKed. This does not appear to be
* a case that can actually occur. Why are we testing it?
* the sequence we already ACKed. This is not an error,
* it can occur when we send a packet directly off of the write_queue
* in a zero window probe.
*/
if (!skb_queue_empty(&sk->write_queue) &&
......
......@@ -325,35 +325,38 @@ void tcp_write_xmit(struct sock *sk)
skb_unlink(skb);
/*
* See if we really need to send the packet.
* See if we really need to send the whole packet.
*/
if (before(skb->end_seq, sk->rcv_ack_seq +1))
{
if (before(skb->end_seq, sk->rcv_ack_seq +1)) {
/*
* This is acked data. We can discard it. This
* cannot currently occur.
* This is acked data. We can discard it.
* This implies the packet was sent out
* of the write queue by a zero window probe.
*/
sk->retransmits = 0;
kfree_skb(skb, FREE_WRITE);
if (!sk->dead)
sk->write_space(sk);
}
else
{
} else {
struct tcphdr *th;
struct iphdr *iph;
int size;
/*
* put in the ack seq and window at this point rather than earlier,
* in order to keep them monotonic. We really want to avoid taking
* back window allocations. That's legal, but RFC1122 says it's frowned on.
* Ack and window will in general have changed since this packet was put
* on the write queue.
*/
iph = skb->ip_hdr;
th = (struct tcphdr *)(((char *)iph) +(iph->ihl << 2));
/* See if we need to shrink the leading packet on
* the retransmit queue. Strictly speaking, we
* should never need to do this, but some buggy TCP
* implementations get confused if you send them
* a packet that contains both old and new data. (Feh!)
* Soooo, we have this uglyness here.
*/
if (after(sk->rcv_ack_seq,skb->seq+th->syn+th->fin))
tcp_shrink_skb(sk,skb,sk->rcv_ack_seq);
size = skb->len - (((unsigned char *) th) - skb->data);
#ifndef CONFIG_NO_PATH_MTU_DISCOVERY
if (size > sk->mtu - sizeof(struct iphdr))
......@@ -363,6 +366,13 @@ void tcp_write_xmit(struct sock *sk)
}
#endif
/*
* put in the ack seq and window at this point rather than earlier,
* in order to keep them monotonic. We really want to avoid taking
* back window allocations. That's legal, but RFC1122 says it's frowned on.
* Ack and window will in general have changed since this packet was put
* on the write queue.
*/
th->ack_seq = htonl(sk->acked_seq);
th->window = htons(tcp_select_window(sk));
......@@ -1190,3 +1200,56 @@ void tcp_send_probe0(struct sock *sk)
sk->prot->retransmits ++;
tcp_reset_xmit_timer (sk, TIME_PROBE0, sk->rto);
}
/*
* Remove the portion of a packet that has already been sent.
* Needed to deal with buggy TCP implementations that can't deal
* with seeing a packet that contains some data that has already
* been received.
*/
void tcp_shrink_skb(struct sock *sk, struct sk_buff *skb, u32 ack)
{
struct iphdr *iph;
struct tcphdr *th;
unsigned char *old, *new;
unsigned long len;
int diff;
/*
* Recover the buffer pointers
*/
iph = (struct iphdr *)skb->ip_hdr;
th = (struct tcphdr *)(((char *)iph) +(iph->ihl << 2));
/* how much data are we droping from the tcp frame */
diff = ack - skb->seq;
/* how much data are we keeping in the tcp frame */
len = (skb->end_seq - (th->fin + th->syn)) - ack;
/* pointers to new start of remaining data, and old start */
new = (unsigned char *)th + th->doff*4;
old = new+diff;
/* Update our starting seq number */
skb->seq = ack;
th->seq = htonl(ack);
iph->tot_len = htons(ntohs(iph->tot_len)-diff);
/* Get the partial checksum for the IP options */
if (th->doff*4 - sizeof(*th) > 0)
skb->csum = csum_partial((void *)(th+1),
th->doff*4-sizeof(*th),0);
else
skb->csum = 0;
/* Copy the good data down and get it's checksum */
skb->csum = csum_partial_copy((void *)old,(void *)new,len,skb->csum);
/* shorten the skb */
skb_trim(skb,skb->len-diff);
/* Checksum the shrunk buffer */
tcp_send_check(th, sk->saddr, sk->daddr,
th->doff * 4 + len , skb);
}
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