39 printf 的输出到设备层的调试

前言

在前面 printf 的调试 我们只是调试到了 glibc 调用系统调用, 封装了参数 stdout, 带输出的字符缓冲, 以及待输出字符长度 

然后内核这边 只是到了 write 的系统调用, 并未向下细看 

我们这里 稍微向下 细追一下, 看看 到达设备层面 这里是怎么具体的 impl 的  

测试用例

测试用例如下, 这里仅仅是一个简单的输出 

(initramfs) cat Test01Sum.c #include "stdio.h"int main(int argc, char** argv) {int x = 2;
int y = 3;
int z = x + y;printf(" x + y = %d\n ", z);}

tty 输出的调试

接着 printf 的调试 的 vfs_write 的这里, 看一下 上下文, 待输出的字符串为 " x + y = 5\n" 

然后 输出的 stdout 文件的 inode_no 为 7407 

inode 7407 在这里对应的设备为 

 (initramfs) ls -ail /dev | grep console7407 crw-------    1    5,   1 console

设备 /dev/console

该字符设备初始化是在 tty_init 的时候进行初始化的 

主设备号位 TTYAUX_MAJOR 为 5, 此设备号位 1, 相关操作 ops 为 console_fops 

vfs 层面 write 操作映射到下层是 console_fops.redirected_tty_write 

console_fops.redirected_tty_write 

关于 tty->tty_ldisc->ops

这层抽象的设计, 等以后有所收获之后 再回来补充 

文件关联的 tty 是来自于 file->private_data 

这一层也有一层抽象, tty->tty_ldisc, 这里对应的是 n_tty_ops 

process_output_block 根据 换行回车, 制表符 分割 输出数据到 tty 

ntty_ops 输出是根据 tty->ops 来写出数据 

关于 tty->ops 

这层抽象的设计, 等以后有所收获之后 再回来补充 

 拷贝待输出数据到 输出缓冲区, 然后 刷出缓冲区

此时暂时无输出 

执行了 __uart_start 之后的某个时间点将待输出数据, 输出 

此时输出情况如下 

接下来是输出 " x + y = 5" 之后的这个 换行回车 

此时输出情况如下 

ntty 的初始化 

ntty 是默认的 tty, 然后 start_kernel 的时候初始化 console 的时候, 首先注册了默认的 ntty 的相关 ops 

tty 的初始化

kernel_init 的时候 serial8250_init 的时候注册了 ttyS 的驱动相关 

kernel_init 的时候, 会尝试 open "/dev/console", 这里会触发 对应的 tty, 以及相关初始化 

如下为 分配了 "/dev/console" 对应的 tty 的空间, 然后初始化 ldisc 为 n_tty_ops 

上面初始化 ntty 将 ntty 注册到了 tty_ldiscs_lock 

初始化 tty->ops 为 driver->ops, 上面的 uart_register_driver 中初始化 driver 的 ops 为 uart_ops 

uart_ops 的定义如下 

从 xmit 的 buf 输出到 8250串口 

这里是接着上面的 __uart_start 之后产生了中断 

然后这里具体的讲 xmit->buf 的数据输出到 8250串口 

之所以叫串口 就是因为它是按照 单字节传输的, 这里循环 待处理的字符输出到 8250串口

将所有输出输出完成之后 会走 uart_circ_empty(xmit) 的判断, 进而 break 跳出循环 

比如这里执行到 第五次循环, 剩余待输出字符为 5 个, "y = 5" 

控制台输出如下 

假设我们键盘录入 'a', 通过 8250 串口输出 'a' 到控制台

向 8250 串口依次输出的是 

7 5 7 97 5 7 5

第一对 "7 5" 是 n_tty 缓冲区接收到 'a' 的输入之后 

有一个 tty->ops->flush_chars, 因为缓冲区没有数据, 因此直接是一个开始字节, 一个结束字节 

第一对中的 "5" 主要是 xmit->buf 中暂时没有待输出的 字节序列, 因此直接 传输了一个结束标记 

开始字节中的 7, 主要是在 up->iter 中打上了 UART_IER_THRI 的标记, 由 0x101 变成了 0x111 

结束字节中的 5, 主要是在 up->iter 中打上了 UART_IER_THRI 的标记, 由 0x111 变成了 0x101 

开始, 结束 的 控制字符意义如下 

7 表示 UART_IER_RDI + UART_IER_THRI + UART_IER_RLSI

5 表示 UART_IER_RDI + UART_IER_RLSI

#define UART_IER_MSI		0x08 /* Enable Modem status interrupt */
#define UART_IER_RLSI		0x04 /* Enable receiver line status interrupt */
#define UART_IER_THRI		0x02 /* Enable Transmitter holding register int. */
#define UART_IER_RDI		0x01 /* Enable receiver data interrupt */

第二对 "7 97 5" 主要是来自于输出了 'a' 到 "/dev/console" 

开始标记, 输出第一个字节 "7" 

'a' 输出到 8250 串口, 主要是来自于本文主讲的内容, 讲 xmit->buf 的数据输出到 8250 串口

第三个字节 "5" 的输出, 主要是 xmit->buf 中的输出完了之后发送的一个结束标记 

第三对 "7 5" 主要是来自于 上面 ntty.n_tty_write 的流程中 process_output_block 之后

有一个 tty->ops->flush_chars 的流程

输出了一个 开始标记, 发现 xmit->buf 中暂无输出数据, 然后输出了一个结束标记 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/32626.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

利用logstash将graylog日志传输到kafka中

1.graylog配置输出 在System-outputs,选择GELF Output,填写如下内容,其它选项默认 在要输出的Stream中,选择Manage Outputs 选择GELF Output,右边选择刚才创建好的test。 2.安装logstash,作为中间临时…

《Java-SE-第三十四章》之Optional

前言 在你立足处深挖下去,就会有泉水涌出!别管蒙昧者们叫嚷:“下边永远是地狱!” 博客主页:KC老衲爱尼姑的博客主页 博主的github,平常所写代码皆在于此 共勉:talk is cheap, show me the code 作者是爪哇岛的新手,水平很有限&…

C#小轮子:Visual Studio自动编译Sass文件

文章目录 前言插件安装插件使用compilerconfig.jsonsass输入和css输出(自动生成)默认配置(我不懂就不去动他了) 前言 我们知道css文件用起来太麻烦,如果样式一多,嵌套起来用css样式就眼花缭乱。Sass使用层…

Kafka的下载和安装

一、Kafka下载和安装 下载地址:https://kafka.apache.org/downloads 下载完毕解压即可 linux解压命令tar -zxvf kafka_2.13-3.5.1.tgz,linux环境下指令是在\kafka_2.13-3.5.1\bin目录。 windows直接解压即可,windows环境下指令是在kafka_2.…

强化学习-信任区域策略优化和近端策略优化(第7章)

来源书籍: TENSORFLOW REINFORCEMENT LEARNING QUICK START GUIDE 《TensorFlow强化学习快速入门指南-使用Python动手搭建自学习的智能体》 著者:[美]考希克巴拉克里希南(Kaushik Balakrishnan) 译者:赵卫东 出版…

Rust 编程小技巧摘选(7)

目录 Rust 编程小技巧(7) 1. 交换变量 2. 翻转数组 3. for_each() 用法 4. 结构体 Display trait 5. HashMap 和 BTreeMap 6. 遍历输出哈希表 7. 分离奇数和偶数 8. 判断素数(质数) Rust 编程小技巧(7) 1. 交换变量 与python, go等语言用法类…

计算机网络:网络字节序

目录 一、字节序1.字节序概念2.字节序的理解(1)大端模式存储数据(2)小端模式存储数据 二、网络字节序 一、字节序 1.字节序概念 字节序:内存中存储多字节数据的顺序。 难道存储数据还要看顺序吗? yes。内…

【将回声引入信号中】在语音或音频文件中引入混响或简单回声,以研究回声延迟和回波幅度对生成的回波信号感知的影响(Matlab代码实现)

💥💥💞💞欢迎来到本博客❤️❤️💥💥 🏆博主优势:🌞🌞🌞博客内容尽量做到思维缜密,逻辑清晰,为了方便读者。 ⛳️座右铭&a…

Java 正则表达式【匹配与分组基本原理】

简介 我们一般使用正则表达式是用来处理字符串的,不管是实际的开发中还是我们的算法竞赛中,使用正则表达式绝对可以大大提升我们的效率。 正则表达式(regular expression)其实就是对字符串进行模式匹配的技术。 快速入门 我们这里…

第三篇|金融人数据来源有哪些

数据对于金融行业真的很重要,那么金融人有哪些途径查数据呢? 国内: 1. 国家统计局 这个应该是无论什么行业都使用最频繁的网站,每个月都会固定发上个月资产投资数据 、工业增加值和利润数据等常规数据,其他数据也会…

什么是分布式系统,如何学习分布式系统

正文 虽然本人在前面也写过好几篇分布式系统相关的文章,主要包CAP理论,分布式储存与分布式事务,但对于分布式系统,并没有一个跟清晰的概念。分布式系统涉及到很多的技术、理论与协议,很多人也说,分布式系统…

Docker 安装和架构说明

Docker 并非是一个通用的容器工具,它依赖于已存在并运行的Linux内核环境。 Docker实质上是在已经运行的Liunx下制造了一个隔离的文件环境,因此他的执行效率几乎等同于所部署的linux主机。因此Docker必须部署在Linux内核系统上。如果其他系统想部署Docke…

hutool 导出复杂表头excel

假如已这样的表头导出数据 1.把包含表头的excel添加到项目资源目录 2.编写代码读取表头所在sheet,并且加入需导出的数据 /*** 导出excel*/public static void downloadExcel(List<List<Object>> list, HttpServletResponse response) throws IOException {/*Strin…

wpf 3d 坐标系和基本三角形复习

wpf 3d 坐标系的描述见此&#xff0c; WPF 3d坐标系和基本三角形_wpf 坐标系_bcbobo21cn的博客-CSDN博客 X轴正向向右&#xff0c;Y轴正向向上&#xff1b;Z轴&#xff0c;正向是从屏幕里边出来&#xff0c;负向是往屏幕里边去&#xff1b;坐标原点是在呈现区域的中心&#x…

知识付费系统开发:构建高效智能的付费内容平台

随着数字化时代的来临&#xff0c;知识付费正迅速崭露头角&#xff0c;为知识创作者和求知者带来了全新的商机。在这个背景下&#xff0c;开发一款高效智能的知识付费系统成为了一项重要的任务。本文将深入探讨如何基于Python编程语言和相关技术构建一个智能的知识付费内容平台…

mac arm 通过brew搭建 php+nginx+mysql+xdebug

1.安装nginx brew install nginx //安装brew services start nginx //启动2.安装php brew install php7.4 //安装export PATH"/opt/homebrew/opt/php7.4/bin:$PATH" //加入环境变量 export PATH"/opt/homebrew/opt/php7.4/sbin:$PATH"brew serv…

【百度翻译api】中文自动翻译为英文

欸&#xff0c;最近想做一些nlp的项目&#xff0c;做完了中文的想做做英文的&#xff0c;但是呢&#xff0c;国内爬虫爬取的肯定都是中文 &#xff0c;爬取外网的技术我没有尝试过&#xff0c;没有把握。所以我决定启用翻译&#xff0c;在这期间chatGPT给了我非常多的方法&…

【枚举】CF1660 D

Problem - 1660D - Codeforces 题意&#xff1a; 思路&#xff1a; 思路巨简单&#xff0c;代码也wa了很多发才过&#xff0c;都是因为细节.... 很显然&#xff0c;要根据0分段处理 对于每一段&#xff0c;枚举去掉左边段还是右边段&#xff0c;左边段是 l 到第一个负数&am…

网络加速与文件传输软件:如何通过优化网络提升文件传输速度

在信息化社会&#xff0c;文件传输是人们生活和工作中必不可少的一个环节。但是&#xff0c;由于网络环境的多样性和传输过程中可能出现的各种问题&#xff0c;文件传输速度经常受到影响。因此&#xff0c;如何优化网络以提高文件传输速度成为了一个重要的课题。本文将探讨网络…

力扣:59. 螺旋矩阵 II(Python3)

题目&#xff1a; 给你一个正整数 n &#xff0c;生成一个包含 1 到 n2 所有元素&#xff0c;且元素按顺时针顺序螺旋排列的 n x n 正方形矩阵 matrix 。 来源&#xff1a;力扣&#xff08;LeetCode&#xff09; 链接&#xff1a;力扣&#xff08;LeetCode&#xff09;官网 - 全…