c - 从头开始在内核中写入串行端口 COM1

标签 c serial-port kernel i386

我正在从头开始编写 i386 ELF 内核。我需要能够写入串行端口 COM1。

我写了两个函数,每次调用 printk(char* str) 时都会调用 serial_init(),它会调用每个字符的每次迭代 serial_putc (字符 c)

#define SERIAL_COM1 (0x03f8)

void serial_putc(char c)
{
    char* serial = (char*)SERIAL_COM1;

    while ((serial[5] & 0x20) == 0);
    serial[0] = c;
}

void serial_init()
{
    char* serial = (char*)SERIAL_COM1;

    serial[1] = 0x00;
    serial[3] = 0x80;
    serial[0] = 0x03;
    serial[1] = 0x00;
    serial[3] = 0x03;
    serial[2] = 0xc7;
    serial[4] = 0x0b;
}

线路协议(protocol)是:

  • 38400 波特
  • 每个字 8 位
  • 无奇偶校验
  • 1个停止位

我正在使用 qemu-system-i386 -serial stdio -kernel ./kernel 来测试我的内核,但它不会在串行端口的输出上打印任何内容。

因为我需要编写 outbinb 这里是代码:

inline void outb(unsigned int port, unsigned char val)
{
    asm volatile ("outb %%al,%%dx": :"d" (port), "a" (val));
}

inline unsigned char inb(unsigned int port)
{
    unsigned char ret;

    asm volatile ("inb %%dx,%%al":"=a" (ret):"d" (port));
    return (ret);
}

我仍然无法得到输出。
我做错了什么?

最佳答案

你应该看看 outb() 和 inb(),你不能这样写你的 COM1 地址。

关于c - 从头开始在内核中写入串行端口 COM1,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33358955/

相关文章:

c - 确定字符串是否为 C 中的有效 wchar_t*

使用 Xcode 控制到达非 void 函数 C 编程的末尾

iOS - 串行通信集成到 Xcode 项目中

delphi - 在delphi中分割串行数据

linux - 为什么在查看一个目录时 inotify 会出错,而在另一个目录下却不会出错?

assembly - 如何读取特定内核的(性能计数器)寄存器?

operating-system - 驱动程序如何成为内核的一部分?

c - linux中的signal,int 0x80是谁调用的?

c - 如何修复我的 C 程序?

C#串口,模拟串口写入