当前位置: 首页 > news >正文

Ubuntu 下 nginx-1.24.0 源码分析 - ngx_cpuinfo 函数

ngx_cpuinfo

声明在 src/core/ngx_core.h

void ngx_cpuinfo(void);

定义在 src/core/ngx_cpuinfo.c

这里 ngx_cpuinfo 的定义可以找到 2 个

使用 gcc -E 处理一下来确认当下环境中使用的是哪一个

gcc -E src/core/ngx_cpuinfo.c \-I src/core \-I src/event \-I src/event/modules \-I src/os/unix \-I objs \> ngx_cpuinfo_preprocessed.c

在 输出文件中 查找 ngx_cpuinfo

void
ngx_cpuinfo(void)
{u_char *vendor;uint32_t vbuf[5], cpu[4], model;vbuf[0] = 0;vbuf[1] = 0;vbuf[2] = 0;vbuf[3] = 0;vbuf[4] = 0;ngx_cpuid(0, vbuf);vendor = (u_char *) &vbuf[1];if (vbuf[0] == 0) {return;}ngx_cpuid(1, cpu);if (strcmp((const char *) vendor, (const char *) "GenuineIntel") == 0) {switch ((cpu[0] & 0xf00) >> 8) {case 5:ngx_cacheline_size = 32;break;case 6:ngx_cacheline_size = 32;model = ((cpu[0] & 0xf0000) >> 8) | (cpu[0] & 0xf0);if (model >= 0xd0) {ngx_cacheline_size = 64;}break;case 15:ngx_cacheline_size = 128;break;}} else if (strcmp((const char *) vendor, (const char *) "AuthenticAMD") == 0) {ngx_cacheline_size = 64;}
}

 详解 src\core\ngx_cpuinfo.c

/** Copyright (C) Igor Sysoev* Copyright (C) Nginx, Inc.*/#include <ngx_config.h>
#include <ngx_core.h>#if (( __i386__ || __amd64__ ) && ( __GNUC__ || __INTEL_COMPILER ))static ngx_inline void ngx_cpuid(uint32_t i, uint32_t *buf);#if ( __i386__ )static ngx_inline void
ngx_cpuid(uint32_t i, uint32_t *buf)
{/** we could not use %ebx as output parameter if gcc builds PIC,* and we could not save %ebx on stack, because %esp is used,* when the -fomit-frame-pointer optimization is specified.*/__asm__ ("    mov    %%ebx, %%esi;  ""    cpuid;                ""    mov    %%eax, (%1);   ""    mov    %%ebx, 4(%1);  ""    mov    %%edx, 8(%1);  ""    mov    %%ecx, 12(%1); ""    mov    %%esi, %%ebx;  ": : "a" (i), "D" (buf) : "ecx", "edx", "esi", "memory" );
}#else /* __amd64__ */static ngx_inline void
ngx_cpuid(uint32_t i, uint32_t *buf)
{uint32_t  eax, ebx, ecx, edx;__asm__ ("cpuid": "=a" (eax), "=b" (ebx), "=c" (ecx), "=d" (edx) : "a" (i) );buf[0] = eax;buf[1] = ebx;buf[2] = edx;buf[3] = ecx;
}#endif/* auto detect the L2 cache line size of modern and widespread CPUs */void
ngx_cpuinfo(void)
{u_char    *vendor;uint32_t   vbuf[5], cpu[4], model;vbuf[0] = 0;vbuf[1] = 0;vbuf[2] = 0;vbuf[3] = 0;vbuf[4] = 0;ngx_cpuid(0, vbuf);vendor = (u_char *) &vbuf[1];if (vbuf[0] == 0) {return;}ngx_cpuid(1, cpu);if (ngx_strcmp(vendor, "GenuineIntel") == 0) {switch ((cpu[0] & 0xf00) >> 8) {/* Pentium */case 5:ngx_cacheline_size = 32;break;/* Pentium Pro, II, III */case 6:ngx_cacheline_size = 32;model = ((cpu[0] & 0xf0000) >> 8) | (cpu[0] & 0xf0);if (model >= 0xd0) {/* Intel Core, Core 2, Atom */ngx_cacheline_size = 64;}break;/** Pentium 4, although its cache line size is 64 bytes,* it prefetches up to two cache lines during memory read*/case 15:ngx_cacheline_size = 128;break;}} else if (ngx_strcmp(vendor, "AuthenticAMD") == 0) {ngx_cacheline_size = 64;}
}#elsevoid
ngx_cpuinfo(void)
{
}#endif

 

代码整体结构

#if (( __i386__ || __amd64__ ) && ( __GNUC__ || __INTEL_COMPILER ))static ngx_inline void ngx_cpuid(uint32_t i, uint32_t *buf);#if ( __i386__ )
static ngx_inline void ngx_cpuid(uint32_t i, uint32_t *buf) { ... }
#else /* __amd64__ */
static ngx_inline void ngx_cpuid(uint32_t i, uint32_t *buf) { ... }
#endifvoid ngx_cpuinfo(void) { ... }#elsevoid ngx_cpuinfo(void) { }#endif

条件编译指令

#if (( __i386__ || __amd64__ ) && ( __GNUC__ || __INTEL_COMPILER ))

 

  • 作用
    这段代码仅在以下条件下编译:
    • 目标平台是 x86 或 x86-64 架构
    • 编译器是 GCC 或 Intel 编译器
  • 原因
    • CPUID 是 x86/x86-64 架构特有的指令,其他架构(如 ARM)不支持。
    • GCC 和 Intel 编译器支持类似的内联汇编语法,而其他编译器可能不支持。

ngx_cpuid 函数声明

static ngx_inline void ngx_cpuid(uint32_t i, uint32_t *buf);
  • 作用
    声明一个内联函数 ngx_cpuid,用于调用 CPUID 指令并存储结果。
  • 参数说明

    • uint32_t i:输入参数,表示 CPUID 的功能号。
    • uint32_t *buf:输出缓冲区,用于存储 CPUID 返回的四个寄存器值(EAX、EBX、ECX、EDX)。
  • 修饰符

    • static:限制函数的作用域为当前文件,避免符号冲突。
    • ngx_inline:提示编译器将函数展开为内联代码,减少函数调用开销。

        内联函数可以减少函数调用的开销,适合频繁调用的场景。

实现 ngx_cpuid(32 位 x86 架构) 

#if ( __i386__ )
static ngx_inline void
ngx_cpuid(uint32_t i, uint32_t *buf)
{__asm__ ("    mov    %%ebx, %%esi;  ""    cpuid;                ""    mov    %%eax, (%1);   ""    mov    %%ebx, 4(%1);  ""    mov    %%edx, 8(%1);  ""    mov    %%ecx, 12(%1); ""    mov    %%esi, %%ebx;  ": : "a" (i), "D" (buf) : "ecx", "edx", "esi", "memory" );
}

这段代码的核心作用是通过内联汇编调用 CPUID 指令,并将结果存储到指定的缓冲区中 


使用 GCC 风格的内联汇编语法

__asm__ ("汇编指令": 输出操作数: 输入操作数: 被修改的寄存器列表
);

 


"    mov    %%ebx, %%esi;  "
  • 作用
    %ebx 寄存器的值保存到 %esi 寄存器中。

  • 原因

    • 在 32 位模式下,GCC 在生成位置无关代码(PIC,Position Independent Code)时会使用 %ebx 作为基址寄存器。
    • 因此,不能直接将 %ebx 作为输出参数,否则会导致编译错误或运行时问题。
    • 解决方法是先将 %ebx 的值保存到 %esi,然后在后续操作中恢复。

"    cpuid;                "
  • 作用
    调用 CPUID 指令,根据输入的功能号 i 查询处理器信息。

  • 工作原理

    • 输入参数通过 %eax 寄存器传递。
    • 输出结果存储在以下寄存器中:
      • %eax:主信息(如处理器型号)。
      • %ebx%edx%ecx:附加信息(如厂商字符串、特性标志等)

: : "a" (i) 这里指示将 输入的参数 i,加载到 eax 寄存器

CPUID 指令会根据 %eax 中的功能号执行相应的查询操作。

获取结果

查询结果会存储在 %eax%ebx%ecx%edx 寄存器中。

随后,这些寄存器的值会被逐一存储到 buf 数组中。


"    mov    %%eax, (%1);   "

 

  • 作用
    %eax 寄存器的值存储到 buf[0] 中。

  • 细节

    • %1 是内联汇编中的占位符,对应输入操作数 buf
    • (buf) 表示将 %eax 的值存储到 buf 指向的内存地址中。

: : "a" (i), "D" (buf) 对于这个输入输出操作数列表 %0是指 a(i),也就是 eax

"D" (buf) 指示 将变量 buf 的值(即地址)放入 %edi 寄存器中

所以%1 指的是 edi(输入参数buf 的值)

在 x86 汇编中,括号 () 用于表示间接寻址 ,即访问括号内地址所指向的内存内容


"    mov    %%ebx, 4(%1);  "
  • 作用
    %ebx 寄存器的值存储到 buf[1] 中。

  • 4(%1) 表示将 %ebx 的值存储到 buf + 4 的地址中(即 buf[1]

4(%1) 是 x86 汇编语言中的一种内存寻址模式 ,称为基址加偏移量寻址 (Base + Offset Addressing)。

它表示从某个寄存器(基址寄存器)所指向的地址开始,加上一个固定的偏移量,访问对应的内存位置

基本语法是:

offset(base_register)

  • base_register

    • 基址寄存器,存储内存地址的基础值。
    • %1 对应的是 %edi 寄存器。
  • offset

    • 偏移量,表示从基址寄存器所指向的地址开始,向后偏移的字节数。
    • 4(%1) 中,偏移量是 4

"    mov    %%edx, 8(%1);  "
  • 作用
    %edx 寄存器的值存储到 buf[2] 中。

  • 8(%1) 表示将 %edx 的值存储到 buf + 8 的地址中(即 buf[2]

"    mov    %%ecx, 12(%1); "
  • 作用
    %ecx 寄存器的值存储到 buf[3] 中。

  • 12(%1) 表示将 %ecx 的值存储到 buf + 12 的地址中(即 buf[3]

"    mov    %%esi, %%ebx;  "
  • 作用
    将之前保存在 %esi 中的值恢复到 %ebx 寄存器。

  • 原因

    • 恢复 %ebx 的原始值,确保不会破坏调用者的状态。

: : "a" (i), "D" (buf)
  • "a" (i):将变量 i 的值放入 %eax 寄存器。
  • "D" (buf):将变量 buf 的地址放入 %edi 寄存器

: "ecx", "edx", "esi", "memory"
  • 作用
    告诉编译器哪些寄存器或内存被内联汇编修改了。

  • "ecx", "edx", "esi":这些寄存器在汇编代码中被修改。
  • "memory":标记内存操作,确保编译器正确处理缓存一致性

 实现 ngx_cpuid(64 位 x86-64 架构)

#else /* __amd64__ */static ngx_inline void
ngx_cpuid(uint32_t i, uint32_t *buf)
{uint32_t  eax, ebx, ecx, edx;__asm__ ("cpuid": "=a" (eax), "=b" (ebx), "=c" (ecx), "=d" (edx) : "a" (i) );buf[0] = eax;buf[1] = ebx;buf[2] = edx;buf[3] = ecx;
}

同样调用 CPUID 指令,但 64 位环境下可以直接使用 %rbx,无需额外保存

%rbx 不再是特殊用途寄存器。

因此,我们可以直接使用 %rbx,而不需要像 32 位环境中那样担心破坏编译器的逻辑

实现 ngx_cpuinfo 函数
void ngx_cpuinfo(void)
{u_char    *vendor;uint32_t   vbuf[5], cpu[4], model;vbuf[0] = 0;vbuf[1] = 0;vbuf[2] = 0;vbuf[3] = 0;vbuf[4] = 0;ngx_cpuid(0, vbuf);vendor = (u_char *) &vbuf[1];if (vbuf[0] == 0) {return;}ngx_cpuid(1, cpu);if (ngx_strcmp(vendor, "GenuineIntel") == 0) {switch ((cpu[0] & 0xf00) >> 8) {case 5: ngx_cacheline_size = 32; break;case 6:ngx_cacheline_size = 32;model = ((cpu[0] & 0xf0000) >> 8) | (cpu[0] & 0xf0);if (model >= 0xd0) {ngx_cacheline_size = 64;}break;case 15: ngx_cacheline_size = 128; break;}} else if (ngx_strcmp(vendor, "AuthenticAMD") == 0) {ngx_cacheline_size = 64;}
}

函数签名

void ngx_cpuinfo(void)

返回值类型:void

  • 作用

    • 函数没有返回值。
    • 它的主要目的是通过检测 CPU 特性来设置全局变量 ngx_cacheline_size,而不是返回具体的结果。
  • 原因

    • 全局变量的设计使得其他模块可以直接使用 ngx_cacheline_size,无需通过函数返回值传递数据。

定义局部变量

u_char    *vendor;
uint32_t   vbuf[5], cpu[4], model;
  • 作用
    • vendor:指向厂商字符串的指针,用于存储 CPU 厂商信息(如 "GenuineIntel" 或 "AuthenticAMD")。
    • vbuf[5]:用于存储 CPUID 功能号 0 的返回结果(厂商字符串和其他信息)。
    • cpu[4]:用于存储 CPUID 功能号 1 的返回结果(处理器型号和其他特性)。
    • model:用于计算处理器的具体型号。

初始化缓冲区

vbuf[0] = 0;
vbuf[1] = 0;
vbuf[2] = 0;
vbuf[3] = 0;
vbuf[4] = 0;

vbuf 数组的所有元素初始化为 0,避免未初始化的值导致意外行为


调用 CPUID 功能号 0

ngx_cpuid(0, vbuf);

作用
调用 CPUID 指令的功能号 0,获取厂商字符串和其他信息。

功能号 0 的返回值

vbuf[0] = EAX  // 最大基本功能号
vbuf[1] = EBX  // 厂商字符串第一部分
vbuf[2] = EDX  // 厂商字符串第二部分
vbuf[3] = ECX  // 厂商字符串第三部分

获取厂商字符串

vendor = (u_char *) &vbuf[1];
  • 作用
    vbuf[1] 的地址强制转换为 u_char* 类型,指向厂商字符串的起始位置。

  • 原因

    • CPUID 功能号 0 返回的厂商字符串分布在 vbuf[1]vbuf[2]vbuf[3] 中。
    • 通过指针操作可以方便地访问完整的字符串。

检查功能号支持

if (vbuf[0] == 0) {return;
}
  • 作用
    如果 vbuf[0] == 0,表示 CPU 不支持 CPUID 指令或不支持更高的功能号,直接返回。

  • 原因

    • 早期的处理器可能不支持 CPUID 指令,或者仅支持有限的功能号。
    • 在这种情况下,无法继续检测 CPU 特性。

调用 CPUID 功能号 1

ngx_cpuid(1, cpu);
  • 作用
    调用 CPUID 指令的功能号 1,获取处理器的型号和其他特性。

  • 结果存储

    • cpu[0]:包含处理器家族号、型号号等信息
    • cpu[1]cpu[2]cpu[3]:包含其他特性标志(如缓存特性、指令集支持等)

处理 Intel 处理器

if (ngx_strcmp(vendor, "GenuineIntel") == 0) {switch ((cpu[0] & 0xf00) >> 8) {case 5:ngx_cacheline_size = 32;break;case 6:ngx_cacheline_size = 32;model = ((cpu[0] & 0xf0000) >> 8) | (cpu[0] & 0xf0);if (model >= 0xd0) {ngx_cacheline_size = 64;}break;case 15:ngx_cacheline_size = 128;break;}
}
  • 作用
    根据处理器家族号(cpu[0] & 0xf00)设置缓存行大小。

  • 逻辑分析

    1. 家族号提取

      • (cpu[0] & 0xf00) >> 8 提取处理器家族号。
      • 家族号用于区分不同的处理器系列(如 Pentium、Core 等)。
    2. Pentium(家族号 5)

      • 缓存行大小为 32 字节。
    3. Pentium Pro/II/III(家族号 6)

      • 默认缓存行大小为 32 字节。
      • 对于较新的型号(如 Core、Core 2、Atom),缓存行大小为 64 字节。
      • 使用 ((cpu[0] & 0xf0000) >> 8) | (cpu[0] & 0xf0) 计算具体型号。
    4. Pentium 4(家族号 15)

      • 缓存行大小为 128 字节(由于预取机制,实际缓存行为更复杂)。

处理 AMD 处理器

else if (ngx_strcmp(vendor, "AuthenticAMD") == 0) {ngx_cacheline_size = 64;
}
  • 作用
    对于 AMD 处理器,统一设置缓存行大小为 64 字节。

  • 原因

    • AMD 处理器的缓存行大小通常为 64 字节。
    • 无需进一步区分型号。

默认实现

#elsevoid
ngx_cpuinfo(void)
{
}#endif

 

如果目标平台或编译器不满足条件,则提供一个空实现。

确保代码在不支持的平台上也能正常编译,避免错误。

​​​​

相关文章:

Ubuntu 下 nginx-1.24.0 源码分析 - ngx_cpuinfo 函数

ngx_cpuinfo 声明在 src/core/ngx_core.h void ngx_cpuinfo(void); 定义在 src/core/ngx_cpuinfo.c 这里 ngx_cpuinfo 的定义可以找到 2 个 使用 gcc -E 处理一下来确认当下环境中使用的是哪一个 gcc -E src/core/ngx_cpuinfo.c \-I src/core \-I src/event \-I src/event/modu…...

python小项目编程-中级(1、图像处理)

目录 图像处理 实现 测试 unittest pytest 图像处理 实现界面化操作&#xff0c;使用PIL库实现简单的图像处理功能&#xff0c;如缩放&#xff08;设置缩放比例&#xff09;、旋转和滤镜、对比度调整、亮度调整、灰度图、二值化图&#xff08;二值图如果使用的是彩色图片需…...

EasyExcel实现excel导入(模版上传)

目录 效果pom.xmlapplication.ymlcontrollerservice依赖类前台vue代码某个功能如果需要添加大量的数据,通过一条条的方式添加的方式,肯定不合理,本文通过excel导入的方式来实现该功能,100条数据导入成功85条,失败15条,肯定需要返回一个表格给前台或者返回1个错误excel给前…...

AI工作流+专业知识库+系统API的全流程任务自动化

我有点悲观&#xff0c;甚至很沮丧&#xff0c;因为AI留给普通人的机会不多了&#xff0c;这既是人类之间权力的斗争&#xff0c;也是硅基生命和碳基生命的斗争。AI自动化是无法避免的趋势&#xff0c;如果人类不能平权&#xff0c;那就只能跪下接受审判。 通过整合AI工作流、专…...

【C/C++】合并两个有序链表 (leetcode T21)

核心考点预览&#xff1a;链表 &#xff08;双指针&#xff09; 技巧&#xff1a;虚拟头结点 题目描述&#xff1a; 将两个升序链表合并为一个新的 升序 链表并返回。新链表是通过拼接给定的两个链表的所有节点组成的。 示例&#xff1a; 输入输出示例1l1 [1,2,4], l2 [1…...

C语言进阶习题【2】(4结构体进阶)——通讯录的实现3

1. 本节在动态版本通讯录的基础上实现存储功能 在动态版本的基础上&#xff0c;对于通讯录的新增了存储到文件中&#xff0c;可以从文件中打开我们存储的通信录功能。新增函数&#xff1a;saveContatc()和loadContact&#xff08;&#xff09; 2. 具体实现 2.1 contact.h /…...

Linux系统编程之无名管道

概述 在Linux系统中&#xff0c;无名管道是一种简单的进程间通信机制。它允许一个进程创建一对文件描述符&#xff0c;其中一个用于读取&#xff0c;另一个用于写入。当一个进程通过系统调用创建了一个无名管道后&#xff0c;便可以将这两个文件描述符传递给它的子进程&#xf…...

deepseek与其他大模型配合组合

DeepSeek与其他大模型的配合组合&#xff0c;展现了其在多个领域中的强大应用潜力和灵活性。以下是对DeepSeek与其他大模型配合组合的详细分析&#xff1a; 一、DeepSeek与华知大模型的组合 背景介绍&#xff1a; 华知大模型是同方知网与华为联手打造的&#xff0c;具备全学科…...

ASP.NET Core Clean Architecture

文章目录 项目地址一、1. 重点1.1 Repository数据库接口1.2 GetEventDetail 完整的Query流程1.3 创建Command并使用validation 项目地址 教程作者&#xff1a;ASP.NET Core Clean Architecture 2022-12 教程地址&#xff1a; https://www.bilibili.com/video/BV1YZ421M7UA?…...

DeepSeek安装部署笔记(一)

Ollamaopen-WebUI部署 DeepSeek安装部署笔记第一步 Ollama安装1.安装ollama&#xff1a;官网https://ollama.com/下载2.上面安装完成&#xff0c;在cmd命令行&#xff1a; 第二步 给DeepSeek添加OpenWebUI界面&#xff08;重点&#xff09;1.安装conda&#xff1a;用它来管理py…...

ProfiNet转EtherNet/IP罗克韦尔PLC与监控系统通讯案例

一、案例背景 在新能源产业蓬勃发展的当下&#xff0c;大型光伏电站作为绿色能源的重要输出地&#xff0c;其稳定高效的运行至关重要。某大型光伏电站占地面积广阔&#xff0c;内部设备众多&#xff0c;要保障电站的稳定运行&#xff0c;对站内各类设备进行集中监控与管理必不可…...

23.2 HtmlDocument类

版权声明&#xff1a;本文为博主原创文章&#xff0c;转载请在显著位置标明本文出处以及作者网名&#xff0c;未经作者允许不得用于商业目的。 HtmlDocument类提供了HTML文档的顶级编程访问&#xff0c;配合WebBrowser的 Document属性使用&#xff0c;可以获得WebBrowser当前页…...

wordpress adrotate插件 文件上传漏洞

当你爆破进wordpress后台但权限不是管理员的时&#xff0c;如果你有adrotate插件操作权限可以用adrotate的文件上传功能get webshell 该漏洞需要AdRotate版本 < 5.13.3 第一步按顺序点击上传文件 在这里文件一定要压缩成zip格式&#xff0c;上传的时候也是上传这个zip 上…...

数据分析和数据挖掘的工作内容

基本的数据分析工作通常包含以下几个方面的内容&#xff1a; 确定目标&#xff08;输入&#xff09;&#xff1a;理解业务&#xff0c;确定指标口径。获取数据&#xff1a;数据仓库&#xff08;SQL提数&#xff09;、电子表格、三方接口、网络爬虫、开放数据集等。清洗数据&am…...

【Pandas】pandas Series sample

Pandas2.2 Series Computations descriptive stats 方法描述Series.align(other[, join, axis, level, …])用于将两个 Series 对齐&#xff0c;使其具有相同的索引Series.case_when(caselist)用于根据条件列表对 Series 中的元素进行条件判断并返回相应的值Series.drop([lab…...

qt + opengl 给立方体增加阴影

在前几篇文章里面学会了通过opengl实现一个立方体&#xff0c;那么这篇我们来学习光照。 风氏光照模型的主要结构由3个分量组成&#xff1a;环境(Ambient)、漫反射(Diffuse)和镜面(Specular)光照。下面这张图展示了这些光照分量看起来的样子&#xff1a; 1 环境光照(Ambient …...

buuctf-[极客大挑战 2019]Knife题解

一个很简单的web题&#xff0c;进入界面 网页名还加白给的shell&#xff0c;并且给的提示也很明显&#xff0c;给了一个一句话木马再加上菜刀&#xff0c;很怀疑是一个webshell题&#xff0c;那么直接打开蚁剑测试连接拿shell 用提示的一句话木马的密码&#xff0c;测试链接发现…...

常用电脑,护眼软件推荐 f.lux 3400K | 撰写论文 paper

常用电脑&#xff1f;平均每天用 5 个小时&#xff1f;你就要考虑用一个护眼软件了&#xff0c;对皮肤也好。因为电脑屏幕有辐射&#xff0c;比如蓝光。 f.lux 作为一款专业护眼软件&#xff0c;值得使用。之前用了三年的 Iris Pro&#xff0c;现在 f.lux 做的更好了。 使用…...

【操作幂等和数据一致性】保障业务在MySQL和COS对象存储的一致

业务场景 发布信息&#xff0c;更新到数据库MySQLCOS操作&#xff0c;更新JSON文件 不过可能存在幂等性和数据一致性的问题。 // 批量存MySQL entityPublishService.saveOrUpdateBatch(entityPublishList); // 遍历批量存COS对象存储searchEntitys.forEach(req -> {//删除…...

[答疑]领域建模:邓丽君、周杰伦和少女时代

DDD领域驱动设计批评文集 做强化自测题获得“软件方法建模师”称号 《软件方法》各章合集 第五元素 2025-2-18 17:12 潘老师&#xff0c;画线的这句话&#xff0c;在这个类图中怎么体现呢&#xff1f; &#xff08;回答者补注&#xff1a;问题的素材来自《邓丽君的领域建模》…...

【鸿蒙开发】第四十三章 Notification Kit(用户通知服务)

目录​​​​​​​ 1 简介 1.1 使用场景 1.2 能力范围 1.3 业务流程 1.4 通知样式 1.5 约束限制 1.6 与相关Kit的关系 2 请求通知授权 2.1 接口说明 2.2 开发步骤 3 管理通知角标 3.1 接口说明 3.2 开发步骤 4 管理通知渠道 4.1 通知渠道类型说明 4.2 接口说明…...

Ubuntu 20.04源码安装opencv 4.5.0

安装依赖项 sudo apt install -y g sudo apt install -y cmake sudo apt install -y make sudo apt install -y wget unzip安装opencv依赖库 sudo apt-get install build-essential libgtk2.0-dev libgtk-3-dev libavcodec-dev libavformat-dev libjpeg-dev libswscale-dev l…...

buu-get_started_3dsctf_2016-好久不见39

栈溢出外平栈 1外平栈与内平栈的区别 外平栈&#xff1a; 栈帧的局部变量和返回地址之间没有额外的对齐或填充。返回地址直接位于局部变量的上方&#xff08;即栈顶方向&#xff09;。在计算偏移时&#xff0c;不需要额外加 4&#xff08;因为返回地址紧邻局部变量&#xff09…...

一周学会Flask3 Python Web开发-客户端状态信息Cookie以及加密

锋哥原创的Flask3 Python Web开发 Flask3视频教程&#xff1a; 2025版 Flask3 Python web开发 视频教程(无废话版) 玩命更新中~_哔哩哔哩_bilibili HTTP是无状态&#xff08;stateless)协议。也就是说&#xff0c;在一次请求响应结束后&#xff0c;服务器不会留下任何关于对…...

深入解析Qt事件循环

在Qt开发中&#xff0c;QApplication::exec()这行代码是每个开发者都熟悉的“魔法咒语”。为什么GUI程序必须调用它才能响应操作&#xff1f;为何耗时操作会导致界面冻结&#xff1f;本文将以事件循环为核心&#xff0c;揭示Qt高效运转的底层逻辑&#xff0c;探讨其设计哲学与最…...

python中的异常-模块-包

文章目录 异常异常的定义异常捕获语法捕获常规异常捕获指定异常捕获多个异常捕获所有异常异常else异常finally 异常传递总结 模块概念导入自定义模块及导入main方法all变量 总结 包自定义包定义pycharm中建包的基本步骤导入方式 第三方包 异常 异常的定义 当检测到一个错误时…...

AI 百炼成神:线性回归,预测房价

我们开始第一个项目——线性回归:预测房价。这是一个经典的机器学习入门项目,可以帮助你理解如何使用线性回归模型来预测连续的数值。 第一个项目:线性回归预测房价 项目目标 学习线性回归的基本概念。使用历史房价数据建立一个预测模型。理解如何评估模型的性能。项目步骤…...

Grok-3 与 DeepSeek 的技术架构与性能分析

随着 AI 大模型技术的快速发展,Grok-3(xAI)与 DeepSeek-V3/R1(深度求索)成为近期备受关注的焦点。本文将从技术架构、性能表现、成本效率和应用场景等维度,深入对比分析这两大模型的优劣势。 一、技术架构对比 1. DeepSeek-V3/R1:高效 MoE 架构与工程优化 混合专家模型…...

机器学习实战(4):逻辑回归——分类问题的基础

第4集&#xff1a;逻辑回归——分类问题的基础 在机器学习中&#xff0c;逻辑回归&#xff08;Logistic Regression&#xff09; 是解决分类问题的经典算法之一。尽管名字中有“回归”&#xff0c;但它实际上是一种分类模型&#xff0c;广泛应用于二分类任务&#xff08;如垃圾…...

我是如何从 0 到 1 找到 Web3 工作的?

作者&#xff1a;Lotus的人生实验 关于我花了一个月的时间&#xff0c;从 0 到 1 学习 Web3 相关的知识和编程知识。然后找到了一个 Web3 创业公司实习的远程工作。 &#x1f447;&#x1f447;&#x1f447; 我的背景: 计算机科班&#xff0c;学历还可以(大厂门槛水平) 毕业工…...

基于WebRTC与AI大模型接入EasyRTC:打造轻量级、高实时、强互动的嵌入式音视频解决方案

随着物联网和嵌入式技术的快速发展&#xff0c;嵌入式设备对实时音视频通信的需求日益增长。然而&#xff0c;传统的音视频解决方案往往存在体积庞大、实时性差、互动体验不佳等问题&#xff0c;难以满足嵌入式设备的资源限制和应用场景需求。 针对以上痛点&#xff0c;本文将介…...

【DeepSeek】本地部署,保姆级教程

deepseek网站链接传送门&#xff1a;DeepSeek 在这里主要介绍DeepSeek的两种部署方法&#xff0c;一种是调用API&#xff0c;一种是本地部署。 一、API调用 1.进入网址Cherry Studio - 全能的AI助手选择立即下载 2.安装时位置建议放在其他盘&#xff0c;不要放c盘 3.进入软件后…...

Java 大视界 -- 国际竞争与合作:Java 大数据在全球市场的机遇与挑战(94)

&#x1f496;亲爱的朋友们&#xff0c;热烈欢迎来到 青云交的博客&#xff01;能与诸位在此相逢&#xff0c;我倍感荣幸。在这飞速更迭的时代&#xff0c;我们都渴望一方心灵净土&#xff0c;而 我的博客 正是这样温暖的所在。这里为你呈上趣味与实用兼具的知识&#xff0c;也…...

流程绩效分析,实现销售目标的保障

在当今竞争激烈的商业环境里&#xff0c;客户关系管理&#xff08;CRM&#xff09;行业正迎来深刻变革。企业若想在市场中脱颖而出&#xff0c;实现业务的持续增长&#xff0c;流程绩效分析成为关键。通过提供销售全流程绩效分析能力&#xff0c;企业能够针对销售全流程的复杂业…...

Linux NFS

Linux NFS NFS&#xff08;Network File System&#xff09;是一种用于在网络上共享文件系统的协议&#xff0c;允许不同的计算机通过网络访问和共享文件&#xff0c;就像访问本地文件一样。它广泛应用于 Linux 和 UNIX 系统中&#xff0c;支持多用户并发访问&#xff0c;适合…...

一文精通JWT Token、ID Token、Access Token、Refresh Token

JWT Token JSON Web Token (JWT,RFC 7519 (opens new window)),是为了在网络应用环境间传递声明而执行的一种基于 JSON 的开放标准((RFC 7519)。该 token 被设计为紧凑且安全的,特别适用于分布式站点的单点登录(SSO)场景。JWT 的声明一般被用来在身份提供者和服务提供者…...

CSS基础(浮动、相对定位、绝对定位、固定定位、粘性定位、版心、重置默认样式)

文章目录 1. 浮动&#xff08;float&#xff09;1.1 简介1.2 元素浮动后的特点1.3 脱离文档流示例图1.4 浮动产生的影响1.4.1 积极影响1.4.2 消极影响 1.5 解决浮动产生的影响1.5.1 清除浮动&#xff08;Clearfix&#xff09;1.5.2 创建新的块格式化上下文&#xff08;BFC&…...

uniapp中引入Vant Weapp的保姆级教学(包含错误处理)

废话不多说&#xff0c;直接上方法&#xff0c;网上的教学好多都是错误的 1.安装vant weapp 在Hbuilder的终端&#xff0c;输入以下代码 npm install vant/weapp -S --production 2.新建wxcomponents文件夹 在项目的跟目录新建一个“wxcomponents’文件夹&#xff0c;与app.…...

Datawhale Ollama教程笔记5

Dify 接入 Ollama 部署的本地模型 Dify 支持接入 Ollama 部署的大型语言模型推理和 embedding 能力。 快速接入 下载 Ollama 访问 Ollama 安装与配置&#xff0c;查看 Ollama 本地部署教程。 运行 Ollama 并与 Llama 聊天 ollama run llama3.1Copy to clipboardErrorCopied …...

STL —— 洛谷字符串(string库)入门题(蓝桥杯题目训练)(二)

目录 一、B2121 最长最短单词 - 洛谷 算法代码&#xff1a; 代码分析 变量定义 输入处理 单词长度计算 更新最长和最短单词的长度 输出最长单词 输出最短单词 评测记录&#xff1a;​编辑 二、B2122 单词翻转 - 洛谷 算法代码&#xff1a; 代码分析 引入头文件和定…...

P1055 [NOIP 2008 普及组] ISBN 号码(java)【AC代码】

每一本正式出版的图书都有一个 ISBN 号码与之对应&#xff0c;ISBN 码包括 9 位数字、1 位识别码和 3 位分隔符&#xff0c;其规定格式如 x-xxx-xxxxx-x&#xff0c;其中符号 - 就是分隔符&#xff08;键盘上的减号&#xff09;&#xff0c;最后一位是识别码&#xff0c;例如 0…...

JavaScript如何创建一个对象?对象字面量和构造函数创建对象有什么区别?

JavaScript如何创建一个对象&#xff1f;对象字面量和构造函数创建对象有什么区别&#xff1f; JavaScript 创建对象的方式 在 JavaScript 中&#xff0c;有多种方式可以创建对象&#xff0c;这里主要介绍对象字面量和构造函数这两种常见的方式。 1. 对象字面量 对象字面量…...

【量化科普】Sharpe Ratio,夏普比率

【量化科普】Sharpe Ratio&#xff0c;夏普比率 &#x1f680;&#x1f680;&#x1f680;量化软件开通&#x1f680;&#x1f680;&#x1f680; &#x1f680;&#x1f680;&#x1f680;量化实战教程&#x1f680;&#x1f680;&#x1f680; 在量化投资领域&#xff0c;…...

知识蒸馏知识点

1基于kl散度计算,学生模型需要用log_softmax处理 2 为了避免温度对梯度的影响,loss*T**2 操作目的教师 / 学生输出除以 软化概率分布,暴露类别间关系损失乘以 抵消温度对梯度的缩放,维持梯度量级稳定,确保训练收敛性 import torch import torch.nn.functional as F# 原…...

Springboot + Ollama + IDEA + DeepSeek 搭建本地deepseek简单调用示例

1. 版本说明 springboot 版本 3.3.8 Java 版本 17 spring-ai 版本 1.0.0-M5 deepseek 模型 deepseek-r1:7b 需要注意一下Ollama的使用版本&#xff1a; 2. springboot项目搭建 可以集成在自己的项目里&#xff0c;也可以到 spring.io 生成一个项目 生成的话&#xff0c;如下…...

【MySQL】MySQL表的增删改查(进阶)

1.❤️❤️前言~&#x1f973;&#x1f389;&#x1f389;&#x1f389; Hello, Hello~ 亲爱的朋友们&#x1f44b;&#x1f44b;&#xff0c;这里是E绵绵呀✍️✍️。 如果你喜欢这篇文章&#xff0c;请别吝啬你的点赞❤️❤️和收藏&#x1f4d6;&#x1f4d6;。如果你对我的…...

装修流程图: 装修前准备 → 设计阶段 → 施工阶段 → 安装阶段 → 收尾阶段 → 入住

文章目录 引言I 毛坯房装修的全流程**1. 装修前准备****1.1 确定装修预算****1.2 选择装修方式****1.3 选择装修公司****1.4 办理装修手续****2. 设计阶段****2.1 量房****2.2 设计方案****2.3 确认方案****3. 施工阶段****3.1 主体拆改****3.2 水电改造****3.3 防水工程****3.…...

JavaScript系列(79)--Web Worker 高级应用

Web Worker 高级应用 &#x1f504; Web Worker 为JavaScript提供了真正的多线程能力&#xff0c;让我们能够在后台线程中执行复杂的计算而不阻塞主线程。今天让我们深入探讨Web Worker的高级应用。 Web Worker 概述 &#x1f31f; &#x1f4a1; 小知识&#xff1a;Web Work…...

人工智能之自动驾驶技术体系

自动驾驶技术体系 自动驾驶技术是人工智能在交通领域的重要应用&#xff0c;旨在通过计算机视觉、传感器融合、路径规划等技术实现车辆的自主驾驶。自动驾驶不仅能够提高交通效率&#xff0c;还能减少交通事故和环境污染。本文将深入探讨自动驾驶的技术体系&#xff0c;包括感…...

该如何搭建高效的跨境网络专线?

在如今这个全球化的商业环境中&#xff0c;跨境网络专线成为了企业与个人实现高效、安全跨国通信的重要工具。大家好&#xff0c;在接下来的内容中&#xff0c;我将深入为您探讨跨境网络专线的概念、特点以及搭建流程&#xff0c;帮助您更好地理解和利用这一技术。 一、什么是…...