1.skynet源码结构、源码启动流程以及多线程工作原理
2.nginx源码分析--master和worker进程模型
3.源码细读-深入了解terser-webpack-plugin的源码实现
4.Linux内核 kthread_worker 和 kthread_work 机制
skynet源码结构、启动流程以及多线程工作原理
本文主要介绍skynet源码目录结构、源码启动流程以及其多线程工作原理。源码
1、源码skynet目录结构
只允许上层调用下层,源码易语言源码获取而下层不能直接调用上层的源码api,这样做层次清晰。源码
2、源码skynet启动流程
启动skynet方式:终端输入./skynet exmaple/config
启动入口函数为skynet_main.c/main,源码 config作为args[1]参数传入
调用skynet_start.c/skynet_start函数
3、skynet多线程工作原理
线程创建工作由skynet_start.c/start完成,源码主要有以下四类线程:
1、源码moniter线程
初始化该线程的源码key对应的私有数据块
每5s对所有工作线程进行一次检测
调用skynet_monitor_check函数检测线程是否有卡住在某条消息处理
2、timer定时器线程
每隔微秒刷新计时、源码唤醒等待条件触发的源码工作线程并检查是否有终端关闭的信号,如果有则打开log文件,将log输出至文件中,在刷新计时中会对每个时刻的链表进行相应的处理.
3、socket套接字线程
处理所有的蘑菇头源码套接字上的事件,该线程确保所有的工作线程中至少有一条工作线程是处于运行状态的,以便可以处理套接字上的事件。
4、worker工作线程
从全局队列中取出服务队列对其消息进行处理,其运行函数thread_worker的工作原理:首先初始化该线程的key对应的私有数据块,然后从全局队列中取出服务队列对其消息进行处理,最后当全局队列中没有服务队列信息时进入等待状态,等待定时器线程或套接字线程触发条件。
4、skynet消息处理如何保证线程安全?
以上介绍了skynet源码中的目录结构以及各部分功能,接着介绍了skynet的启动流程,最后介绍了skynet的多个线程是如何进行协同工作的。
nginx源码分析--master和worker进程模型
一、Nginx整体架构
正常执行中的nginx会有多个进程,其中最基本的是master process(主进程)和worker process(工作进程),还可能包括cache相关进程。
二、核心进程模型
启动nginx的系统源码包主进程将充当监控进程,主进程通过fork()产生的子进程则充当工作进程。
Nginx也支持单进程模型,此时主进程即是工作进程,不包含监控进程。
核心进程模型框图如下:
master进程
监控进程作为整个进程组与用户的交互接口,负责监护进程,不处理网络事件,不负责业务执行,仅通过管理worker进程实现重启服务、平滑升级、更换日志文件、配置文件实时生效等功能。
master进程通过sigsuspend()函数调用大部分时间处于挂起状态,直到接收到信号。
master进程通过检查7个标志位来决定ngx_master_process_cycle方法的运行:
sig_atomic_t ngx_reap;
sig_atomic_t ngx_terminate;
sig_atomic_t ngx_quit;
sig_atomic_t ngx_reconfigure;
sig_atomic_t ngx_reopen;
sig_atomic_t ngx_change_binary;
sig_atomic_t ngx_noaccept;
进程中接收到的信号对Nginx框架的意义:
还有一个标志位:ngx_restart,仅在master工作流程中作为标志位使用,与信号无关。
核心代码(ngx_process_cycle.c):
ngx_start_worker_processes函数:
worker进程
worker进程主要负责具体任务逻辑,传奇 java源码主要关注与客户端或后端真实服务器之间的数据可读/可写等I/O交互事件,因此工作进程的阻塞点在select()、epoll_wait()等I/O多路复用函数调用处,等待数据可读/写事件。也可能被新收到的进程信号中断。
master进程如何通知worker进程进行某些工作?采用的是信号。
当收到信号时,信号处理函数ngx_signal_handler()会执行。
对于worker进程的工作方法ngx_worker_process_cycle,它主要关注4个全局标志位:
sig_atomic_t ngx_terminate;//强制关闭进程
sig_atomic_t ngx_quit;//优雅地关闭进程(有唯一一段代码会设置它,就是接受到QUIT信号。ngx_quit只有在首次设置为1时,才会将ngx_exiting置为1)
ngx_uint_t ngx_exiting;//退出进程标志位
sig_atomic_t ngx_reopen;//重新打开所有文件
其中ngx_terminate、ngx_quit、ngx_reopen都将由ngx_signal_handler根据接收到的信号来设置。ngx_exiting标志位仅由ngx_worker_cycle方法在退出时作为标志位使用。
核心代码(ngx_process_cycle.c):
源码细读-深入了解terser-webpack-plugin的实现
深入探索 terser-webpack-plugin:代码压缩与优化的秘密</ terser-webpack-plugin 是一款强大的 webpack 插件,它巧妙地融合了 terser 库的默然社区源码功能,旨在为你的 JavaScript 代码带来高效且优雅的压缩体验。要开始使用,只需参考官方文档中关于 minify-options</的配置指导。这款插件在 webpack 的 compilation 阶段大展身手,通过 optimizeChunkAssets</钩子实现了异步的代码优化,核心逻辑则隐藏在了名为 optimise</的神秘函数中。 优化艺术</ 在 optimise</函数的舞台,一场资源名的魔术表演正在上演。它首先从 compilation 中获取资源,接着根据 availableNumberOfCores</动态决定是否启用并行模式,创建适当的 Worker</。在这里,pLimit</起到了关键作用,它巧妙地控制并发任务的数量,确保效率与稳定性并存。紧接着,遍历每一个 assetNames,一个个任务被 scheduleTask 准备就绪,等待着执行。 任务分解</ 而每个任务的核心 scheduleTask,就像拆解谜题一般,包含着获取 asset 信息、代码检查、minify 的选择(Worker 或主线程)、新代码生成和缓存更新,以及对资产内容的即时更新。整个过程紧凑而有序,以资源处理和并发控制为核心。 并行力量</ terser-webpack-plugin 的亮点之一就是其 parallel</功能,能根据你的计算机 CPU 核心数动态启动 worker,巧妙地利用了 jest-worker 线程池,优先选择高性能的 worker_threads 模式。它通过私有任务队列和先进先出 (FIFO) 管理机制,确保了多进程处理的高效性和一致性。 代码简化与压缩</ minify 函数的精妙之处在于,它直接调用 terser 库的强大功能,略过不必要的 comments 处理,通过出口 API 实现代码的高效压缩。这个过程既简洁又高效,确保了代码质量的提升。 全面优化流程</ terser-webpack-plugin 的优化流程井然有序:异步注册 optimizeChunkAssets</,开启多线程编译(Worker),并在 minify 阶段,利用 terser 的强大压缩能力对代码进行深度处理。而 v4 版本更是增添了异步优化点,让并行处理更加灵活和高效。Linux内核 kthread_worker 和 kthread_work 机制
探究 Linux 内核中的 kthread_worker 和 kthread_work 机制,始于我在研究最新版 Linux Spi 驱动时对这部分工作流程的深入了解。kthread_worker 和 kthread_work 实际上是内核线程管理和使用的一种方式,与 work_struct 和 workqueue_struct 机制类似。接下来,让我们从数据结构、使用方式,以及具体实现入手,对 kthread_worker 和 kthread_work 进行深入分析。
1、数据结构
定义 kthread_worker 和 kthread_work 的数据结构位于 include/linux/kthread.h 中。观察结构体定义,可以看出它们之间的紧密联系。
2、使用方式
kthread_worker 作为核心组件,理解其使用方法至关重要。首先,定义并初始化 kthread_worker。接着,为 kthread_worker 创建一个内核线程,用于处理工作。
2.1 准备 kthread_worker
定义 kthread_worker 并初始化它。注意,初始化完成后,需要为 kthread_worker 创建一个内核线程。
2.2 准备 kthread_work
定义 kthread_work 并初始化。为它指定工作函数。
2.3 启动工作
准备好了 worker 和 work 后,如有工作需要处理,将工作挂接到 worker 上。
2.4 执行指定 worker 上的所有工作
将指定 worker 上的所有工作全部执行。
2.5 停止当前线程
了解 Linux 内核源码学习资源。
3、实现源码
分析源码的步骤如下:
3.1 kthread_init_worker
初始化 kthread_worker。设置成员变量为零,并初始化工作列表。
3.2 执行线程 kthread_worker_fn
定义并初始化 kthread_worker 后,调用 kthread_worker_fn 函数,传入 worker 指针。代码逻辑简单,主要涉及状态设置、工作执行等。
3.3 kthread_init_work
清零 kthread_work 类型的工作,并初始化链表元素,最后挂接工作执行函数的指针。
3.4 kthread_queue_work
将初始化完成的 kthread_worker 和 kthread_work 推进执行。调用 kthread_insert_work 将工作添加至列表中,唤醒沉睡的执行线程。
4、总结
kthread_worker 和 kthread_work 机制为 Linux Kernel 提供了一种高效管理内核线程的手段。它们使得驱动等模块开发者能够简便地实现内核线程的使用。