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

linux之调度管理(8)-SMP cpu 的 psci启动

一、psci介绍

   psci是arm提供的一套电源管理接口,当前一共包含0.1、0.2和1.0三个版本。它可被用于以下场景:
(1)cpu的idle管理

(2)cpu hotplug以及secondary cpu启动

(3)系统shutdown和reset

  但该接口不包含dvfs和设备电源管理(如像GPU之类的外设电源管理)功能。

  由于psci与虚拟化以及trust os有一定的关联,为了专注于电源管理相关的实现,故本系列的介绍都不涉及与它们相关的内容。

  下面我们将按照电源管理拓扑结构(power domain)、电源状态(power state)以及armv8安全扩展几个方面介绍psci的一些基础知识

1.1 power domain

        我们前面已经介绍过cpu的拓扑结构,如aarch64架构下每块soc可能会包含多个cluster,而每个cluster又包含多个core,它们共同组成了层次化的拓扑结构。如以下为一块包含2个cluster,每个cluster包含四个core的soc:

        由于其中每个core以及每个cluster的电源都可以独立地执行开关操作,因此若core0 – core3的电源都关闭了,则cluster 0的电源也可以被关闭以降低功耗。若core0 – core3中的任一个core需要上电,则显然cluster 0需要先上电。为了更好地进行层次化电源管理,psci在电源管理流程中将以上这些组件都抽象为power domain。如以下为上例的power domain层次结构:

 其中system level用于管理整个系统的电源,cluster level用于管理某个特定cluster的电源,而core level用于管理一个单独core的电源。

1.2 power state

         由于aarch64架构有多种不用的电源状态,不同电源状态的功耗和唤醒延迟不同。如standby状态会关闭power domain的clock,但并不关闭电源。因此它虽然消除了门电路翻转引起的动态功耗,但依然存在漏电流等引起的静态功耗。故其功耗相对较大,但相应地唤醒延迟就比较低。

  而对于power down状态,会断开对应power domain的电源,因此其不仅消除了动态功耗,还消除了静态功耗,相应地其唤醒延迟就比较高了。

 psci一共为power domain定义了四种power state:

(1)run:电源和时钟都打开,该domain正常工作

(2)standby:关闭时钟,但电源处于打开状态。其寄存器状态得到保存,打开时钟后就可继续运行。功耗相对较大,但唤醒延迟较低。arm执行wfi或wfe指令会进入该状态。

(3)retention:它将core的状态,包括调试设置都保存在低功耗结构中,并使其部分关闭。其状态在从低功耗变为运行时能自动恢复。从操作系统角度看,除了进入方法、延迟等有区别外,其它都与standby相同。它的功耗和唤醒延迟都介于standby和power down之间。

(4)power down:关闭时钟和电源。power domain掉电后,所有状态都丢失,上电以后软件必须重新恢复其状态。它的功耗最低,但唤醒延迟也相应地最高。

        显然,power state的睡眠程度从run到power down逐步加深。而高层级power domain的power state不应低于低层级power domain。如以上例子中core 0 – core 2都为power down状态,而core 3为standby状态,则cluster 0不能为retention或power down状态。同样若cluster 0为standby状态,而cluster 1为run状态,则整个系统必须为run状态。

        当然,若core 0 –core 3都为power down状态,则cluster 1保持其它状态除了增大功耗之外,并没有其它意义,因此也应该将其设置为power down状态。

为了达到上述约束,不同power domain之间的power state具有以下关系:

        psci实现了父leve与子level之间的电源关系协调,如cluster 0中最后一个core被设置为power down状态后,psci就会将该cluster也设置为power donw状态。若其某一个core被设置为run状态,则psci会先将其对应cluster的状态设置为run,然后再设置对应core的电源状态,这也是psci名字的由来(power state coordinate interface)

1.3 armv8的安全扩展

        为了增强arm架构的安全性,aarch64一共实现了secure和non-secure两种安全状态。通过一系列硬件扩展,在cpu执行状态、总线、内存、外设、中断、tlb、cache等方面都实现了两种状态之间的隔离。

        在这种机制下,secure空间的程序可以访问所有secure和non-secure的资源,而non-secure空间的程序只能访问non-secure资源,却不能访问secure资源。从而可以将一些安全关键的资源放到secure空间,以增强其安全性。

  为此aarch64实现了4个异常等级,其中EL3工作在secure空间,而EL0 – EL2既可以工作于secure空间,又可以工作于non-secure空间。不同异常等级及不同secure状态的模式下可运行不同类型软件。

  如secure EL1和El0用于运行trust os内核及其用户态程序,non-secure EL1和El0用于运行普通操作系统内核(如linux)及其用户态程序,EL2用于运行虚拟机的hypervisor。而EL3运行secure monitor程序(通常为bl31),其功能为执行secure和non secure状态切换、消息转发以及提供类似psci等secure空间服务。以下为其示意图:

        psci是工作于non secure EL1(linux内核)和EL3(bl31)之间的一组电源管理接口,其目的是让linux实现具体的电源管理策略,而由bl31管理底层硬件相关的操作。从而将cpu电源控制这种影响系统安全的控制权限放到安全等级更高的层级中,从而提升系统的整体安全性。

  那么psci如何从EL1调用EL3的服务呢?其实它和系统调用是类似的,只是系统调用是用户态程序陷入操作系统内核,而psci是从操作系统内核陷入secure monitor。armv8提供了一条smc异常指令,内核只需要提供合适的参数后,触发该指令即可通过异常的方式进入secure monitor。

二、psci软件架构

由于psci是由linux内核调用bl31中的安全服务,实现cpu电源管理功能的。因此其软件架构包含三个部分:
(1)内核与bl31之间的调用接口规范

(2)内核中的架构

(3)bl31中的架构

2.1 psci接口规范

psci规定了linux内核调用bl31中电源管理相关服务的接口规范,它包含实现以下功能所需的接口:
(1)cpu idle管理

(2)向系统动态添加或从系统动态移除cpu,通常称为hotplug

(3)secondary cpu启动

(4)系统的shutdown和reset

  psci接口规定了命令对应的function_id、接口的输入参数以及返回值。 其中输入参数可通过x0 – x7寄存器传递,而返回值通过x0 – x4寄存器传递。

  如secondary cpu启动或cpu hotplug时可调用cpu_on接口,为一个cpu执行上电操作。该接口的格式如下:
(1)function_id:0xc400 0003

(2)输入参数:使用mpidr值表示的target cpu id

       cpu启动入口的物理地址

       context id,该值用于表示本次调用上下文相关的信息

(3)返回值:可以为success、invalid_parameter、invalid_address、already_on、on_pending或internal_failure

  有了以下这些接口的详细定义,内核和bl31就只需按照该接口的规定,独立开发psci相关功能。从而避免了它们之间的耦合,简化了开发复杂度。

2.2 内核中的psci架构

        内核psci软件架构包含psci驱动和每个cpu的cpu_ops回调函数实现两部分。其中psci驱动实现了驱动初始化和psci相关接口实现功能,而cpu_ops回调函数最终也会调用psci驱动的接口。

2.2.1 psci驱动

首先我们看一下devicetree中的配置:

psci {compatible = "arm,psci-0.2";  (1)method = "smc";               (2)}

(1)用于指定psci版本

(2)根据该psci由bl31处理还是hypervisor处理,可以指定其对应的陷入方式。若由bl31处理为smc,若由hypervisor处理则为hvc

目前我开发的英伟达板子上的设备树信息:

驱动流程主要是与bl31通信,以确认其是否支持给定的psci版本,以及相关psci操作函数的实现,其流程如下:

其主要工作即为psci设置相关的回调函数,该函数定义如下:

// kernel/drivers/firmware/psci/psci.cstatic void __init psci_0_2_set_functions(void)
{pr_info("Using standard PSCI v0.2 function IDs\n");psci_ops.get_version = psci_get_version;--------------------(1)psci_function_id[PSCI_FN_CPU_SUSPEND] =PSCI_FN_NATIVE(0_2, CPU_SUSPEND);psci_ops.cpu_suspend = psci_cpu_suspend;psci_function_id[PSCI_FN_CPU_OFF] = PSCI_0_2_FN_CPU_OFF;psci_ops.cpu_off = psci_cpu_off;psci_function_id[PSCI_FN_CPU_ON] = PSCI_FN_NATIVE(0_2, CPU_ON);psci_ops.cpu_on = psci_cpu_on;psci_function_id[PSCI_FN_MIGRATE] = PSCI_FN_NATIVE(0_2, MIGRATE);psci_ops.migrate = psci_migrate;psci_ops.affinity_info = psci_affinity_info;psci_ops.migrate_info_type = psci_migrate_info_type;pm_power_off = psci_sys_poweroff;---------------------(2)arm_pm_restart = psci_sys_reset;set_system_pmic_post_power_off_handler(psci_sys_poweroff);---(3)
}

(1)为psci_ops设置相应的回调函数

(2)为psci模块设置系统重启时的通知函数

(3)将系统的power_off函数指向相应的psci接口

这里补充一点:psci-1.0 也是先基于psci-0.2 初始化的。下面是内核源码。

static const struct of_device_id psci_of_match[] __initconst = {{ .compatible = "arm,psci",     .data = psci_0_1_init},{ .compatible = "arm,psci-0.2", .data = psci_0_2_init},{ .compatible = "arm,psci-1.0", .data = psci_1_0_init},{},
};static int __init psci_1_0_init(struct device_node *np)
{int err;err = psci_0_2_init(np);if (err)return err;if (psci_has_osi_support()) {pr_info("OSI mode supported.\n");/* Default to PC mode. */psci_set_osi_mode(false);}return 0;
}
2.2.2 cpu_ops接口

        驱动初始化完成后,cpu的cpu_ops就可以调用这些回调实现psci功能的调用。如下所示,当devicetree中cpu的enable-method设置为psci时,该cpu的cpu_ops将指向cpu_psci_ops。

cpu0: cpu@0 {...enable-method = "psci";…
}

其中cpu_psci_ops的定义如下:

//kernel/arch/arm64/kernel/psci.cconst struct cpu_operations cpu_psci_ops = {.name           = "psci",.cpu_init       = cpu_psci_cpu_init,.cpu_prepare    = cpu_psci_cpu_prepare,.cpu_boot       = cpu_psci_cpu_boot,
#ifdef CONFIG_HOTPLUG_CPU.cpu_can_disable = cpu_psci_cpu_can_disable,.cpu_disable    = cpu_psci_cpu_disable,.cpu_die        = cpu_psci_cpu_die,.cpu_kill       = cpu_psci_cpu_kill,
#endif
};

如启动cpu的接口为cpu_psci_cpu_boot,它会通过以下流程最终调用psci驱动中的psci_ops函数:

static int cpu_psci_cpu_boot(unsigned int cpu)
{phys_addr_t pa_secondary_entry = __pa_symbol(function_nocfi(secondary_entry));int err = psci_ops.cpu_on(cpu_logical_map(cpu), pa_secondary_entry);if (err)pr_err("failed to boot CPU%d (%d)\n", cpu, err);return err;
}

2.3 bl31中的psci架构(是安全系统optee-os 中的内核)

 bl31为内核提供了一系列运行时服务,psci作为其标准运行时服务的一部分,通过宏DECLARE_RT_SVC注册到系统中。其相应的定义如下:

DECLARE_RT_SVC(std_svc,OEN_STD_START,OEN_STD_END,SMC_TYPE_FAST,std_svc_setup,std_svc_smc_handler
)

        其中std_svc_setup会在bl31启动流程中被调用,以用于初始化该服务相关的配置。而std_svc_smc_handler为其smc异常处理函数,当内核通过psci接口调用相关服务时,最终将由该函数执行实际的处理流程。

上图为psci初始化相关的流程,它主要包含内容:

(1)前面我们已经介绍过power domain相关的背景,即psci需要协调不同层级的power domain状态,因此其必须要了解系统的power domain配置情况。以上流程中红色虚线框的部分主要就是用于初始化系统的power domain拓扑及其状态

(2)由于psci在执行电源相关接口时,最终需要操作实际的硬件。而它们是与架构相关的,因此其操作函数最终需要注册到平台相关的回调中。plat_setup_psci_ops即用于注册特定平台的psci_ops回调,其格式如下:

typedef struct plat_psci_ops {void (*cpu_standby)(plat_local_state_t cpu_state);int (*pwr_domain_on)(u_register_t mpidr);void (*pwr_domain_off)(const psci_power_state_t *target_state);void (*pwr_domain_suspend_pwrdown_early)(const psci_power_state_t *target_state);void (*pwr_domain_suspend)(const psci_power_state_t *target_state);void (*pwr_domain_on_finish)(const psci_power_state_t *target_state);void (*pwr_domain_on_finish_late)(const psci_power_state_t *target_state);void (*pwr_domain_suspend_finish)(const psci_power_state_t *target_state);void __dead2 (*pwr_domain_pwr_down_wfi)(const psci_power_state_t *target_state);void __dead2 (*system_off)(void);void __dead2 (*system_reset)(void);int (*validate_power_state)(unsigned int power_state,psci_power_state_t *req_state);int (*validate_ns_entrypoint)(uintptr_t ns_entrypoint);void (*get_sys_suspend_power_state)(psci_power_state_t *req_state);int (*get_pwr_lvl_state_idx)(plat_local_state_t pwr_domain_state,int pwrlvl);int (*translate_power_state_by_mpidr)(u_register_t mpidr,unsigned int power_state,psci_power_state_t *output_state);int (*get_node_hw_state)(u_register_t mpidr, unsigned int power_level);int (*mem_protect_chk)(uintptr_t base, u_register_t length);int (*read_mem_protect)(int *val);int (*write_mem_protect)(int val);int (*system_reset2)(int is_vendor,int reset_type, u_register_t cookie);
}

最后我们再看一下psci操作相应的异常处理流程:

        即其会根据function id的值,分别执行相应的电源管理服务,如启动cpu时会调用psci_cpu_on函数,重启系统时会调用psci_system_rest函数等。

三、secondary cpu启动

        由于psci方式启动secondary cpu的流程,除了其所执行的cpu_ops不同之外,其它流程与spin-table方式是相同的,因此我们这里只给出执行流程图,详细分析可以参考上篇博文。其中以下流程执行secondary cpu启动相关的一些初始化工作:

在初始化完成且hotplug线程创建完成后,就可通过以下流程唤醒cpu hotplug线程:

此后hotplug线程将调用psci回调函数,并最终触发smc异常进入bl31:

bl31接收到该异常后执行std_svc_smc_handler处理函数,并最终调用平台相关的电源管理接口,完成cpu的上电工作,以下为其执行流程:

平台相关回调函数pwr_domain_on将为secondary cpu设置入口函数,然后为其上电使该cpu跳转到内核入口secondary_entry处开始执行。以下为其内核启动流程:

相关文章:

linux之调度管理(8)-SMP cpu 的 psci启动

一、psci介绍 psci是arm提供的一套电源管理接口,当前一共包含0.1、0.2和1.0三个版本。它可被用于以下场景: (1)cpu的idle管理 (2)cpu hotplug以及secondary cpu启动 (3)系统shutdo…...

review-消息中间件MQ

RabbitMQ RabbitMQ,作为当今流行的开源消息代理软件,以其卓越的可靠性、灵活性和易用性在微服务架构和分布式系统中扮演着至关重要的角色。它不仅能够确保消息在不同系统组件间的高效传递,还能通过其高级消息队列协议(AMQP&#x…...

leetcode400第N位数字

代码 class Solution {public int findNthDigit(int n) {int base 1;//位数int weight 9;//权重while(n>(long)base*weight){//300n-base*weight;base;weight*10;}//n111 base3 weight900;n--;int res (int)Math.pow(10,base-1)n/base;int index n%base;return String…...

前端网页开发学习(HTML+CSS+JS)有这一篇就够!

目录 HTML教程 ▐ 概述 ▐ 基础语法 ▐ 文本标签 ▐ 列表标签 ▐ 表格标签 ▐ 表单标签 CSS教程 ▐ 概述 ▐ 基础语法 ▐ 选择器 ▐ 修饰文本 ▐ 修饰背景 ▐ 透明度 ▐ 伪类 ▐ 盒子模型 ▐ 浮动 ▐ 定位 JavaScript教程 ▐ 概述 ▐ 基础语法 ▐ 函数 …...

CSS遮罩:mask

CSS属性 mask 允许使用者通过遮罩或者裁切特定区域的图片的方式来隐藏一个元素的部分或者全部可见区域。 // 一般用位图图片做遮罩 mask: url(~/assets/images/mask.png); mask-size: 100% 100%;// 使用 SVG 图形中的形状来做遮罩 mask: url(~/assets/images/mask.svg#star);…...

Swift闭包的本质

1 闭包的本质其实是一个引用类型:存储在堆空间上,由堆分配空间,且生命周期由ARC(自动引用计数机制)管理 2 捕获值:闭包会捕获上下文使用到的变量(引用类型会保持引用关系)&#xff…...

时代变迁对传统机器人等方向课程的巨大撕裂

2020年之后,全面转型新质课程规划,传统课程规划全部转为经验。 农耕-代表性生产关系-封建分配制度主要生产力-人力工业-代表性生产关系-资本分配制度工业分为机械时代,电气时代,信息时代;主要生产力-人力转为人脑&…...

【算法设计与分析实训】第1关:求序列的最大字段和

务描述 本关任务:编写用动态规划解决最大字段和问题。 相关知识 为了完成本关任务,你需要掌握:动态规划。 编程要求 给定由n个整数(可能为负数)组成的序列:a1,a2,……,an, 求该序列的最大子段和。当所有整…...

【澜舟科技-注册/登录安全分析报告】

前言 由于网站注册入口容易被机器执行自动化程序攻击,存在如下风险: 暴力破解密码,造成用户信息泄露,不符合国家等级保护的要求。短信盗刷带来的拒绝服务风险 ,造成用户无法登陆、注册,大量收到垃圾短信的…...

【读书笔记-《网络是怎样连接的》- 7】Chapter3_2 路由器

本篇继续介绍路由器及其转发过程。 1 路由器内部结构 路由器内部结构图如图所示。 即主要包含左侧的包转发模块和右侧的端口模块。转发模块负责查找包的发送目的地,端口模块完成包的发送。通过安装不同的硬件,转发模块不仅可以支持以太网,也…...

Android Activity 基础接口知识和常见问题

Activity 知识点及问题点 接口onMultiWindowModeChangedonConfigurationChanged 常见问题Android解决点击桌面图标,就重新启动应用程序问题 接口 onMultiWindowModeChanged 定义 onMultiWindowModeChanged是Android中Activity类的一个回调方法。它会在活动&#xf…...

利用python 检测当前目录下的所有PDF 并转化为png 格式

以下是一个完整的 Python 脚本,用于检测当前目录下的所有 PDF 文件并将每一页转换为 PNG 格式: import os from pdf2image import convert_from_path# 设置输出图像的 DPI(分辨率) DPI 300# 获取当前目录 current_directory os…...

解决 Spring Boot 中 `Ambiguous mapping. Cannot map ‘xxxController‘ method` 错误

前言 在使用 Spring Boot 开发 Web 应用时,经常会遇到各种各样的错误。其中一种常见的错误是 Ambiguous mapping. Cannot map ‘testController‘ method。本文将详细介绍这个错误的原因及解决方法,帮助开发者快速定位并解决问题。 错误解释 这个错误…...

C++ 函数返回值优化

本文中部分内容来自下面的文章,还有一部分来自智谱清言 C 返回值优化_c 局部变量返回优化-CSDN博客 elision:省略 copy elision:拷贝省略 RVO (Return Value Optimization):返回值优化 ------ 我最近也遇到了上面博文中说到的问题&…...

c++源码阅读__ThreadPool__正文阅读

一. 简介 本章我们开始阅读c git 高星开源项目ThreadPool, 这是一个纯c的线程池项目, 并且代码量极小, 非常适合新手阅读 git地址: progschj / ThreadPool 二. 前提知识 为了面对不同读者对c掌握情况不同的情况, 这里我会将基本上稍微值得一说的前提知识点, 全部专门写成一篇…...

关于ES的查询

查询结果那么多字段都是什么? 为什么会提到这个问题呢,因为默认ES查询的结果会有很多信息,我们可能并不希望要那么多数据,所以你需要了解这些字段都表示什么,并正确的返回和使用它们。 took– Elasticsearch 运行查询…...

数据结构初识

目录 1.初识 2.时间复杂度 常见时间复杂度举例: 3.空间复杂度 4.包装类&简单认识泛型 4.1装箱和拆箱 5.泛型 6.泛型的上界 7.泛型方法 8.List接口 1.初识 1.多画图 2.多思考 3.多写代码 4.多做题 牛客网-题库/在线编程/剑指offer 算法篇&#xff1a…...

保存数据到Oracle时报错ORA-17004: 列类型无效: 1111

1、问题描述: 关键信息:Mybatis;Oracle (1)保存信息到Oracle时报错: Caused by: org.apache.ibatis.type.TypeException: Error setting null for parameter #10 with JdbcType OTHER . Try setting a dif…...

Excel——宏教程(1)

Microsoft excel是一款功能非常强大的电子表格软件。它可以轻松地完成数据的各类数学运算,并用各种二维或三维图形形象地表示出来,从而大大简化了数据的处理工作。但若仅利用excel的常用功能来处理较复杂的数据,可能仍需进行大量的人工操作。…...

论文浅尝 | MindMap:知识图谱提示激发大型语言模型中的思维图(ACL2024)

笔记整理:和东顺,天津大学硕士,研究方向为软件缺陷分析 论文链接:https://aclanthology.org/2024.acl-long.558/ 发表会议:ACL 2024 1. 动机 虽然大语言模型(LLMs)已经在自然语言理解和生成任务…...

第6章:TDengine 标签索引和删除数据

TDengine 标签索引和删除数据 目标 掌握标签索引的创建、删除掌握超表、子表创建以及数据删除删除数据 删除数据是 TDengine 提供的根据指定时间段删除指定表或超级表中数据记录的功能,方便用户清理由于设备故障等原因产生的异常数据。 注意:删除数据并不会立即释放该表所…...

【微软:多模态基础模型】(5)多模态大模型:通过LLM训练

欢迎关注[【youcans的AGI学习笔记】](https://blog.csdn.net/youcans/category_12244543.html)原创作品 【微软:多模态基础模型】(1)从专家到通用助手 【微软:多模态基础模型】(2)视觉理解 【微…...

海外带云仓多语言商城源码,多语言多商家云仓一键代发商城

新增海外仓,云仓国际供应链系统,商家可登陆云仓进行批量发货 商城修复了一些bug以及增加了订单数字提示,优化加载速度,二开了一些细微功能 基于 PHP Laravel 框架开发的一款 Web 商城系统。 1.前端多国语言自由切换,…...

android:taskAffinity 对Activity退出时跳转的影响

android:taskAffinity 对Activity跳转的影响 概述taskAffinity 的工作机制taskAffinity对 Activity 跳转的影响一个实际的开发问题总结参考 概述 在 Android 开发中,任务栈(Task)是一个核心概念。它决定了应用程序的 Activity 如何相互交互以…...

Apache Dolphinscheduler数据质量源码分析

Apache DolphinScheduler 是一个分布式、易扩展的可视化数据工作流任务调度系统,广泛应用于数据调度和处理领域。 在大规模数据工程项目中,数据质量的管理至关重要,而 DolphinScheduler 也提供了数据质量检查的计算能力。本文将对 Apache Do…...

solana链上智能合约开发案例一则

环境搭建 安装Solana CLI:Solana CLI是开发Solana应用的基础工具。你可以通过官方文档提供的安装步骤,在本地环境中安装适合你操作系统的Solana CLI版本。安装完成后,使用命令行工具进行配置,例如设置网络环境(如开发网…...

使用 PyTorch 实现 ZFNet 进行 MNIST 图像分类

在本篇博客中,我们将通过两个主要部分来演示如何使用 PyTorch 实现 ZFNet,并在 MNIST 数据集上进行训练和测试。ZFNet(ZFNet)是基于卷积神经网络(CNN)的图像分类模型,广泛用于图像识别任务。 环…...

车轮上的科技:Spring Boot汽车新闻集散地

1系统概述 1.1 研究背景 随着计算机技术的发展以及计算机网络的逐渐普及,互联网成为人们查找信息的重要场所,二十一世纪是信息的时代,所以信息的管理显得特别重要。因此,使用计算机来管理汽车资讯网站的相关信息成为必然。开发合适…...

IDEA2023 SpringBoot整合Web开发(二)

一、SpringBoot介绍 由Pivotal团队提供的全新框架,其设计目的是用来简化Spring应用的初始搭建以及开发过程。该框架使用了特定的方式来进行配置,从而使开发人员不再需要定义样板化的配置。SpringBoot提供了一种新的编程范式,可以更加快速便捷…...

国产三维CAD 2025新动向:推进MBD模式,联通企业设计-制造数据

本文为CAD芯智库原创整理,未经允许请勿复制、转载! 上一篇文章阿芯分享了影响企业数字化转型的「MBD」是什么、对企业优化产品设计流程有何价值——这也是国产三维CAD软件中望3D 2024发布会上,胡其登先生(中望软件产品规划与GTM中…...

宁夏交通厅建设局网站/贵州seo技术查询

你是否喜欢一些小众且无广告的软件?如果是的话,我这边有一些给你推荐的。 1.取色工具——ColorPix ​ ColorPix是一款简单的取色工具,可以随时捕捉屏幕上的颜色,并显示其RGB值和十六进制代码。ColorPix还支持放大镜和颜色锁定功…...

自动推送百度wordpress/东莞网络公司代理

现在基本上所有的网站都需要设置敏感词过滤,似乎已经成了一个网站的标配,如果你的网站没有,或者你没有做相应的处理,那么小心相关部门请你喝茶哦。 最近在调研Java web网站的敏感词过滤的实现,网上找了相关资料&#x…...

济南企业网站制/网络营销与直播电商专升本

在现代工程领域,CAD软件是必不可少的伙伴。无论是机械、建筑、电子工程等领域,CAD软件都是设计和制造过程中的关键要素。 然而,在不同阶段和不同领域使用CAD软件的人员,往往会使用不同版本的CAD软件。这就会导致在不同人员之间交…...

百度推广必须做手机网站吗/淘宝怎么优化关键词步骤

(1)设置对话框的vertical scrollbar属性为true; (2)初始化滚动条,如下:   SCROLLINFO scrollinfo;GetScrollInfo(SB_VERT, &scrollinfo, SIF_ALL);scrollinfo.nPage 10; //设置滑块大小scrollinfo.nMax 75; //设置滚动条的最大位置0--75S…...

无锡专业网站制作的公司/房产网站模板

数据结构与算法总览 文章目录数据结构与算法总览1、职业训练:拆分知识点、刻意练习、反馈(1)Chunk it up 切碎知识点数据结构算法(2)Deliberate Practicing 刻意练习(3)Feedback反馈2、五步刷题…...

团购网站建设流程/山东seo优化

一、下载windows版本mysql8安装包 最好的建议是去oracle官网下载,我下载的是mysql-8.0.25版,安装包已经上传到百度网盘: 链接:https://pan.baidu.com/s/1MOdvw7p1MVYMAVN6EMBJTA 提取码:fodz 二、安装 1、把压缩包放…...