DF-5083 / straddle.c
/* * DF-5083 on-path trigger attempt: issue 64KB reads from the nata-controlled * ATAPI device (acd0/cd0 on the PIIX3 IDE controller) through a buffer that * straddles 17 pages and, once userland has consumed the low 4GB, consists * of pages above 4GB -> the nata data tag must bounce 17 pages against a * 16-page pool -> bus_dmamap_load() == EINPROGRESS -> queued forever -> * the channel wedges ("setting up DMA failed" from then on). */ #include <stdio.h> #include <stdlib.h> #include <string.h> #include <unistd.h> #include <fcntl.h> #include <errno.h> int main(int argc, char **argv) { const char *dev = argc > 1 ? argv[1] : "/dev/cd0"; unsigned char *p; size_t bufsz = 64 * 1024; ssize_t n; long total = 0; int fd, i; p = malloc(bufsz + 4096); if (!p) { perror("malloc"); return 1; } p += 2048; /* misalign: 64KB now straddles 17 pages */ fd = open(dev, O_RDONLY); if (fd < 0) { perror(dev); return 1; } for (i = 0; i < 4096; i++) { n = read(fd, p, bufsz); if (n < 0) { printf("read %d failed after %ld bytes: %s\n", i, total, strerror(errno)); printf("=> if this is EIO/'Input/output error' after " "a DMA-setup failure, the nata channel wedged " "(DF-5083 on-path wedge)\n"); return 2; } total += n; if (n == 0) break; } printf("read %ld bytes OK\n", total); return 0; } |