c++ - USB 大容量存储 linux

标签 c++ c linux-device-driver

<分区>

我是 linux 设备驱动程序的新手。我想编写一个 C/C++ 代码来执行从树莓派到 USB 闪存驱动器的文件传输。我的起点很困难,所以我尝试在 libusb 上使用 signal11 的 HID 设备示例代码,该代码可以很好地检测我的光学鼠标及其设备 ID。然后我尝试以某种方式获取 USB 闪存驱动器供应商 ID,它给了我非常有线的号码。最后我做了一个非常愚蠢的尝试,通过为 cp 文件编写一个 bash 脚本到 usb 闪存驱动器并在 C++ 中激活脚本并且它有效但我觉得这不是一个正确的方法。然后我从 SCSI 协议(protocol)开始,我很难理解它是如何工作的。任何指南都值得赞赏。

int scsi_get_serial(int fd, void *buf, size_t buf_len) {
// we shall retrieve page 0x80 as per http://en.wikipedia.org/wiki/SCSI_Inquiry_Command
unsigned char inq_cmd[] = {INQUIRY, 1, 0x80, 0, buf_len, 0};
unsigned char sense[32];
struct sg_io_hdr io_hdr;
        int result;

memset(&io_hdr, 0, sizeof (io_hdr));
io_hdr.interface_id = 'S';
io_hdr.cmdp = inq_cmd;
io_hdr.cmd_len = sizeof (inq_cmd);
io_hdr.dxferp = buf;
io_hdr.dxfer_len = buf_len;
io_hdr.dxfer_direction = SG_DXFER_FROM_DEV;
io_hdr.sbp = sense;
io_hdr.mx_sb_len = sizeof (sense);
io_hdr.timeout = 5000;

result = ioctl(fd, SG_IO, &io_hdr);
if (result < 0)
    return result;

if ((io_hdr.info & SG_INFO_OK_MASK) != SG_INFO_OK)
    return 1;

return 0;
}

int main(int argc, char** argv) {
//char *dev = "/dev/sda";
char *dev = "/dev/sg2";
char scsi_serial[255];
int rc;
int fd;

fd = open(dev, O_RDONLY | O_NONBLOCK);
if (fd < 0) {
    perror(dev);
}

memset(scsi_serial, 0, sizeof (scsi_serial));
rc = scsi_get_serial(fd, scsi_serial, 255);
// scsi_serial[3] is the length of the serial number
// scsi_serial[4] is serial number (raw, NOT null terminated)
if (rc < 0) {
    printf("FAIL, rc=%d, errno=%d\n", rc, errno);
} else
if (rc == 1) {
    printf("FAIL, rc=%d, drive doesn't report serial number\n", rc);
} else {
    if (!scsi_serial[3]) {
        printf("Failed to retrieve serial for %s\n", dev);
        return -1;
    }
    printf("Serial Number: %.*s\n", (size_t) scsi_serial[3], (char *) & scsi_serial[4]);
}
close(fd);

return (EXIT_SUCCESS);
}

我得到这个序列号:00/1F

然后我尝试在 test.sh 中写这个

cp /home/Desktop/stl4.pdf /media/mini_flash

并在 C++ 中运行 system("./test.sh")

最佳答案

这个问题似乎很矛盾,起初你说你想使用内核驱动程序复制文件,至少可以说这看起来很奇怪。然后你说你使用 libusb,它是一个用户空间库。然后你说你试图用 cp 执行一个 shell 脚本。 也许您想要的只是一个从用户空间 C/C++ 程序复制文件的代码片段?尝试 one of these snippets .

详细来说,如果您要做的只是 C++ 等价于 cp/home/Desktop/STL4.pdf/media/mini_flash,那么这就足够了:

ifstream in("/home/Desktop/stl4.pdf",ios::binary);
ofstream out("/media/mini_flash/stl4.pdf",ios::binary);
out<<in.rdbuf();
in.close();
out.close();

关于c++ - USB 大容量存储 linux,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18183122/

相关文章:

c++ - 如何删除特定节点是二叉搜索树?

c++ - 根据结尾类型对文件路径文件进行排序(超过 7000 行)

c++ - 告诉 Windows 处理除一条消息以外的所有消息

将数组元素连接成 32 位数字

multithreading - 澄清 request_threaded_irq 的行为

linux - 调整linux内核

c++ - 为什么左值引用不能绑定(bind)到 const "forwarding references"?

c - 可以有多个#define吗?

C 是否有允许动态函数调用的解决方法?

Linux 字符驱动程序 : blocking ioctl call