1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23#define FOR_eject
24#include "toys.h"
25#include <scsi/sg.h>
26#include <scsi/scsi.h>
27#include <linux/cdrom.h>
28
29
30static void remove_scsi(int fd)
31{
32 unsigned i;
33 sg_io_hdr_t *header = (sg_io_hdr_t *)(toybuf+64);
34 char sg_driver_cmd[][6] = {
35 { ALLOW_MEDIUM_REMOVAL, 0, 0, 0, 0, 0 },
36 { START_STOP, 0, 0, 0, 1, 0 },
37 { START_STOP, 0, 0, 0, 2, 0 }
38 };
39
40 header->interface_id = 'S';
41 header->cmd_len = 6;
42 header->mx_sb_len = 32;
43 header->dxfer_direction = SG_DXFER_NONE;
44 header->dxferp = toybuf + 32;
45 header->sbp = (void *)toybuf;
46 header->timeout = 2000;
47
48 for (i = 0; i < ARRAY_LEN(sg_driver_cmd); i++) {
49 header->cmdp = (void *)sg_driver_cmd[i];
50 xioctl(fd, SG_IO, header);
51 }
52
53
54 ioctl(fd, BLKRRPART);
55}
56
57void eject_main(void)
58{
59 int fd = xopen(*toys.optargs ? : "/dev/cdrom", O_RDONLY | O_NONBLOCK);
60
61 if (FLAG(s)) remove_scsi(fd);
62 else if (FLAG(T) && CDS_TRAY_OPEN == ioctl(fd, CDROM_DRIVE_STATUS, toybuf))
63 xioctl(fd, CDROMCLOSETRAY, toybuf);
64 else xioctl(fd, CDROMEJECT, toybuf);
65 if (CFG_TOYBOX_FREE) xclose(fd);
66}
67