鸿蒙轻内核M核源码分析:中断Hwi
在鸿蒙轻内核源码分析系列中,本文将深入探讨中断模块,源码暴大量公式源码旨在帮助读者理解中断相关概念、台源鸿蒙轻内核中断模块的源码源代码实现。本文所涉及源码基于OpenHarmony LiteOS-M内核,台源读者可通过开源站点 gitee.com/openharmony/k... 获取。源码中断概念介绍
中断机制允许CPU在特定事件发生时暂停当前执行的台源任务,转而处理该事件。源码这些事件通常由外部设备触发,台源通过中断信号通知CPU。源码中断涉及硬件设备、台源中断控制器和CPU三部分:设备产生中断信号;中断控制器接收信号并发出中断请求给CPU;CPU响应中断,执行中断处理程序。中断相关的好哥俩源码论坛硬件介绍
硬件层面,中断源分为设备、中断控制器和CPU。设备产生中断信号;中断控制器接收并转发这些信号至CPU;CPU在接收到中断请求后,暂停当前任务,转而执行中断处理程序。中断相关的概念
每个中断信号都附带中断号,用于识别中断源。中断优先级根据事件的重要性和紧迫性进行划分。当设备触发中断后,CPU中断当前任务,执行中断处理程序。中断处理程序由设备特定,且通常以中断向量表中的地址作为入口点。中断向量表按中断号排序,存储中断处理程序的地址。鸿蒙轻内核中断源代码
中断相关的声明和定义
在文件 kernel\arch\arm\cortex-m7\gcc\los_interrupt.c 中定义了结构体、全局变量和内联函数。免费php空间源码关键变量 g_intCount 记录当前正在处理的中断数量,内联函数 HalIsIntActive() 用于检查是否正在处理中断。中断向量表在中断初始化过程中设置,用于映射中断号到相应的中断处理程序。中断初始化 HalHwiInit()
系统启动时,在 kernel\src\los_init.c 中初始化中断。HalHwiInit() 函数在 kernel\arch\arm\cortex-m7\gcc\los_interrupt.c 中实现,负责设置中断向量表和优先级组,配置中断源,如系统中断和定时器中断。创建中断 HalHwiCreate()
开发者可通过 HalHwiCreate() 函数注册中断处理程序,传入中断号、优先级和中断模式。函数内部验证参数,设置中断处理程序,最终通过调用 CMSIS 函数完成中断创建。删除中断 HalHwiDelete()
中断删除操作通过 HalHwiDelete() 实现,cf辅助菜单源码接收中断号作为参数,调用 CMSIS 函数失能中断,设置默认中断处理程序,完成中断删除。中断处理执行入口程序
默认的中断处理程序 HalHwiDefaultHandler() 仅用于打印中断号后进行死循环。HalInterrupt() 是中断处理执行入口程序的核心,它包含中断数量计数、中断号获取、中断前后的操作以及调用中断处理程序的逻辑。开关中断
开关中断用于控制CPU是否响应外部中断。通过宏 LOS_IntLock() 关闭中断, LOS_IntRestore() 恢复中断状态, LOS_IntUnLock() 使能中断。这组宏对应汇编函数,使用寄存器 PRIMASK 控制中断状态。小结
本文详细解析了鸿蒙轻内核中断模块的源代码,涵盖了中断概念、酷我音乐 源码初始化、创建、删除以及开关操作。后续文章将带来更多深入技术分享。欢迎在 gitee.com/openharmony/k... 分享学习心得、提出问题或建议。关注、点赞、Star 和 Fork 到个人账户,便于获取更多资源。基于恒玄BES的轻量级鸿蒙操作系统AIOT开发平台解析之SDK下载和编译
一 鸿蒙系统
华为鸿蒙系统作为一款面向全场景的分布式操作系统,旨在构建一个互联世界,通过智能设备间的无缝连接和资源分享,优化用户的全场景生活体验。此系统具有高开源性,兼容多芯片平台,在产业发展中快速推进。
二 恒玄BES
BES芯片由恒玄科技推出,集WiFi和蓝牙功能于一体,具备轻量级和强大资源的特点,特别适用于以音频为中心的高端物联网应用。
三 代码下载和编译
1 源码在Gitee平台上开放,下载地址如下:
gitee.com/openharmony/d...
具体下载步骤如下:
mkdir openharmony_bestechnic
cd openharmony_bestechnic
repo init -u gitee.com/openharmony/m... --no-repo-verify
repo sync -c
repo forall -c 'git lfs pull'
2 使用的是arm-gcc编译器,与鸿蒙系统进行封装和映射,编译命令示例如下:
hb set -root .
hb set -p bestechnic > display_demo iotlink_demo xts_demo
选择display_demo
hb build -f
编译完成会显示:
四 下载和运行
已包含下载指南。编译后的文件会与下载软件和bin文件捆绑,只需将文件复制到Windows环境并按照指示操作即可完成运行。
求一个JAVA计算器源代码。不要按钮的那种。速度。。急用
import java.awt.*;
import java.awt.event.*;
import java.lang.*;
import javax.swing.*;
public class Counter extends Frame
{
//声明三个面板的布局
GridLayout gl1,gl2,gl3;
Panel p0,p1,p2,p3;
JTextField tf1;
TextField tf2;
Button b0,b1,b2,b3,b4,b5,b6,b7,b8,b9,b,b,b,b,b,b,b,b,b,b,b,b,b,b,b,b,b;
StringBuffer str;//显示屏所显示的字符串
double x,y;//x和y都是运算数
int z;//Z表示单击了那一个运算符.0表示"+",1表示"-",2表示"*",3表示"/"
static double m;//记忆的数字
public Counter()
{
gl1=new GridLayout(1,4,,0);//实例化三个面板的布局
gl2=new GridLayout(4,1,0,);
gl3=new GridLayout(4,5,,);
tf1=new JTextField();//显示屏
tf1.setHorizontalAlignment(JTextField.RIGHT);
tf1.setEnabled(false);
tf1.setText("0");
tf2=new TextField();//显示记忆的索引值
tf2.setEditable(false);
//实例化所有按钮、设置其前景色并注册监听器
b0=new Button("Backspace");
b0.setForeground(Color.red);
b0.addActionListener(new Bt());
b1=new Button("CE");
b1.setForeground(Color.red);
b1.addActionListener(new Bt());
b2=new Button("C");
b2.setForeground(Color.red);
b2.addActionListener(new Bt());
b3=new Button("MC");
b3.setForeground(Color.red);
b3.addActionListener(new Bt());
b4=new Button("MR");
b4.setForeground(Color.red);
b4.addActionListener(new Bt());
b5=new Button("MS");
b5.setForeground(Color.red);
b5.addActionListener(new Bt());
b6=new Button("M+");
b6.setForeground(Color.red);
b6.addActionListener(new Bt());
b7=new Button("7");
b7.setForeground(Color.blue);
b7.addActionListener(new Bt());
b8=new Button("8");
b8.setForeground(Color.blue);
b8.addActionListener(new Bt());
b9=new Button("9");
b9.setForeground(Color.blue);
b9.addActionListener(new Bt());
b=new Button("/");
b.setForeground(Color.red);
b.addActionListener(new Bt());
b=new Button("sqrt");
b.setForeground(Color.blue);
b.addActionListener(new Bt());
b=new Button("4");
b.setForeground(Color.blue);
b.addActionListener(new Bt());
b=new Button("5");
b.setForeground(Color.blue);
b.addActionListener(new Bt());
b=new Button("6");
b.setForeground(Color.blue);
b.addActionListener(new Bt());
b=new Button("*");
b.setForeground(Color.red);
b.addActionListener(new Bt());
b=new Button("%");
b.setForeground(Color.blue);
b.addActionListener(new Bt());
b=new Button("1");
b.setForeground(Color.blue);
b.addActionListener(new Bt());
b=new Button("2");
b.setForeground(Color.blue);
b.addActionListener(new Bt());
b=new Button("3");
b.setForeground(Color.blue);
b.addActionListener(new Bt());
b=new Button("-");
b.setForeground(Color.red);
b.addActionListener(new Bt());
b=new Button("1/X");
b.setForeground(Color.blue);
b.addActionListener(new Bt());
b=new Button("0");
b.setForeground(Color.blue);
b.addActionListener(new Bt());
b=new Button("+/-");
b.setForeground(Color.blue);
b.addActionListener(new Bt());
b=new Button(".");
b.setForeground(Color.blue);
b.addActionListener(new Bt());
b=new Button("+");
b.setForeground(Color.red);
b.addActionListener(new Bt());
b=new Button("=");
b.setForeground(Color.red);
b.addActionListener(new Bt());
//实例化四个面板
p0=new Panel();
p1=new Panel();
p2=new Panel();
p3=new Panel();
//创建一个空字符串缓冲区
str=new StringBuffer();
//添加面板p0中的组件和设置其在框架中的位置和大小
p0.add(tf1);
p0.setBounds(,,,);
//添加面板p1中的组件和设置其在框架中的位置和大小
p1.setLayout(gl1);
p1.add(tf2);
p1.add(b0);
p1.add(b1);
p1.add(b2);
p1.setBounds(,,,);
//添加面板p2中的组件并设置其的框架中的位置和大小
p2.setLayout(gl2);
p2.add(b3);
p2.add(b4);
p2.add(b5);
p2.add(b6);
p2.setBounds(,,,);
//添加面板p3中的组件并设置其在框架中的位置和大小
p3.setLayout(gl3);//设置p3的布局
p3.add(b7);
p3.add(b8);
p3.add(b9);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.add(b);
p3.setBounds(,,,);
//设置框架中的布局为空布局并添加4个面板
setLayout(null);
add(p0);
add(p1);
add(p2);
add(p3);
setResizable(false);//禁止调整框架的大小
//匿名类关闭窗口
addWindowListener(new WindowAdapter(){
public void windowClosing(WindowEvent e1)
{
System.exit(0);
}
});
setBackground(Color.lightGray);
setBounds(,,,);
setVisible(true);
}
//构造监听器
class Bt implements ActionListener
{
public void actionPerformed(ActionEvent e2)
{
try{
if(e2.getSource()==b1)//选择"CE"清零
{
tf1.setText("0");//把显示屏清零
str.setLength(0);//清空字符串缓冲区以准备接收新的输入运算数
}
else if(e2.getSource()==b2)//选择"C"清零
{
tf1.setText("0");//把显示屏清零
str.setLength(0);
}
else if(e2.getSource()==b)//单击"+/-"选择输入的运算数是正数还是负数
{
x=Double.parseDouble(tf1.getText().trim());
tf1.setText(""+(-x));
}
else if(e2.getSource()==b)//单击加号按钮获得x的值和z的值并清空y的值
{
x=Double.parseDouble(tf1.getText().trim());
str.setLength(0);//清空缓冲区以便接收新的另一个运算数
y=0d;
z=0;
}
else if(e2.getSource()==b)//单击减号按钮获得x的值和z的值并清空y的值
{
x=Double.parseDouble(tf1.getText().trim());
str.setLength(0);
y=0d;
z=1;
}
else if(e2.getSource()==b)//单击乘号按钮获得x的值和z的值并清空y的值
{
x=Double.parseDouble(tf1.getText().trim());
str.setLength(0);
y=0d;
z=2;
}
else if(e2.getSource()==b)//单击除号按钮获得x的值和z的值并空y的值
{
x=Double.parseDouble(tf1.getText().trim());
str.setLength(0);
y=0d;
z=3;
}
else if(e2.getSource()==b)//单击等号按钮输出计算结果
{
str.setLength(0);
switch(z)
{
case 0 : tf1.setText(""+(x+y));break;
case 1 : tf1.setText(""+(x-y));break;
case 2 : tf1.setText(""+(x*y));break;
case 3 : tf1.setText(""+(x/y));break;
}
}
else if(e2.getSource()==b)//单击"."按钮输入小数
{
if(tf1.getText().trim().indexOf(′.′)!=-1)//判断字符串中是否已经包含了小数点
{
}
else//如果没数点有小
{
if(tf1.getText().trim().equals("0"))//如果初时显示为0
{
str.setLength(0);
tf1.setText((str.append("0"+e2.getActionCommand())).toString());
}
else if(tf1.getText().trim().equals(""))//如果初时显示为空则不做任何操作
{
}
else
{
tf1.setText(str.append(e2.getActionCommand()).toString());
}
}
y=0d;
}
else if(e2.getSource()==b)//求平方根
{
x=Double.parseDouble(tf1.getText().trim());
tf1.setText("数字格式异常");
if(x<0)
tf1.setText("负数没有平方根");
else
tf1.setText(""+Math.sqrt(x));
str.setLength(0);
y=0d;
}
else if(e2.getSource()==b)//单击了"%"按钮
{
x=Double.parseDouble(tf1.getText().trim());
tf1.setText(""+(0.*x));
str.setLength(0);
y=0d;
}
else if(e2.getSource()==b)//单击了"1/X"按钮
{
x=Double.parseDouble(tf1.getText().trim());
if(x==0)
{
tf1.setText("除数不能为零");
}
else
{
tf1.setText(""+(1/x));
}
str.setLength(0);
y=0d;
}
else if(e2.getSource()==b3)//MC为清除内存
{
m=0d;
tf2.setText("");
str.setLength(0);
}
else if(e2.getSource()==b4)//MR为重新调用存储的数据
{
if(tf2.getText().trim()!="")//有记忆数字
{
tf1.setText(""+m);
}
}
else if(e2.getSource()==b5)//MS为存储显示的数据
{
m=Double.parseDouble(tf1.getText().trim());
tf2.setText("M");
tf1.setText("0");
str.setLength(0);
}
else if(e2.getSource()==b6)//M+为将显示的数字与已经存储的数据相加要查看新的数字单击MR
{
m=m+Double.parseDouble(tf1.getText().trim());
}
else//选择的是其他的按钮
{
if(e2.getSource()==b)//如果选择的是"0"这个数字键
{
if(tf1.getText().trim().equals("0"))//如果显示屏显示的为零不做操作
{
}
else
{
tf1.setText(str.append(e2.getActionCommand()).toString());
y=Double.parseDouble(tf1.getText().trim());
}
}
else if(e2.getSource()==b0)//选择的是“BackSpace”按钮
{
if(!tf1.getText().trim().equals("0"))//如果显示屏显示的不是零
{
if(str.length()!=1)
{
tf1.setText(str.delete(str.length()-1,str.length()).toString());//可能抛出字符串越界异常
}
else
{
tf1.setText("0");
str.setLength(0);
}
}
y=Double.parseDouble(tf1.getText().trim());
}
else//其他的数字键
{
tf1.setText(str.append(e2.getActionCommand()).toString());
y=Double.parseDouble(tf1.getText().trim());
}
}
}
catch(NumberFormatException e){
tf1.setText("数字格式异常");
}
catch(StringIndexOutOfBoundsException e){
tf1.setText("字符串索引越界");
}
}
}
public static void main(String args[])
{
new Counter();
}
}
PyTorch 源码分析(三):torch.nn.Norm类算子
PyTorch源码详解(三):torch.nn.Norm类算子深入解析
Norm类算子在PyTorch中扮演着关键角色,它们包括BN(BatchNorm)、LayerNorm和InstanceNorm。1. BN/LayerNorm/InstanceNorm详解
BatchNorm(BN)的核心功能是对每个通道(C通道)的数据进行标准化,确保数据在每个批次后保持一致的尺度。它通过学习得到的gamma和beta参数进行缩放和平移,保持输入和输出形状一致,同时让数据分布更加稳定。 gamma和beta作为动态调整权重的参数,它们在BN的学习过程中起到至关重要的作用。2. Norm算子源码分析
继承关系:Norm类在PyTorch中具有清晰的继承结构,子类如BatchNorm和InstanceNorm分别继承了其特有的功能。
BN与InstanceNorm实现:在Python代码中,BatchNorm和InstanceNorm的实例化和计算逻辑都包含对输入数据的2D转换,即将其分割为M*N的矩阵。
计算过程:在计算过程中,首先计算每个通道的均值和方差,这是这些标准化方法的基础步骤。
C++侧的源码洞察
C++实现中,对于BatchNorm和LayerNorm,代码着重于处理数据的标准化操作,同时确保线程安全,通过高效的数据视图和线程视图处理来提高性能。微信小程序源码转换为uniapp vue3/vite源码
uniapp目前支持vue3语法,对于微信小程序代码迁移至uniapp vue3,转换工作量大。借助自动转换工具,可实现源码自动转换,保持代码可读性。
自动转换原理涉及三个编译器:wxml-compiler、wxss-compiler和wxjs-compiler。它们分别负责将wxml、wxss和wxjs转换为适合vue3/uniapp3的模板、样式和脚本。
wxml-compiler将wxml转换为posthtml-parser解析的AST,通过转换生成新的AST,再使用posthtml-render输出为vue3/uniapp3模板。
wxss-compiler将wxss转换为postcss-parser解析的AST,经历转换生成新的AST,最后通过postcss-render输出为vue3/uniapp3样式。
wxjs-compiler则将wxjs转换为@babel/parser解析的AST,进行转换后生成新的AST,利用@babel/generator输出为vue3/uniapp3脚本。
一个自动转换工具名为miniprogram2vue3,该工具提供转换服务,开发者可通过github项目地址github.com/jacksplwxy/m...获取。
UOS终极波动指标源码的组成要素:综合三个不同周期的RSI
在金融市场投资中,捕捉价格趋势转折点与波动变化是至关重要的。UOS终极波动指标,由拉里·威廉姆斯创造,综合三个不同周期的相对强弱指标(RSI),通过计算其加权平均值,更准确地反映市场动态。UOS指标的金叉和死叉是交易信号的关键依据,分别表示买入与卖出时机。超买超卖区域则帮助投资者识别市场状态,当数值超过或低于特定阈值时,可能出现调整或反转。使用UOS指标时,建议结合主图分析以提升决策稳健性。以下为UOS指标的源码,适用于文华6、7、8等软件,仅供策略思路拓展,投资需谨慎。
N1:=5;
N2:=;
N3:=;
M:=;
HH:=MAX(HIGH,REF(CLOSE,1));
LL:=MIN(LOW,REF(CLOSE,1));
AA:=SUM(CLOSE-LL,N1)/SUM(HH-LL,N1);
BB:=SUM(CLOSE-LL,N2)/SUM(HH-LL,N2);
CC:=SUM(CLOSE-LL,N3)/SUM(HH-LL,N3);
UOS:(AA/N1+BB/N2+CC/N3)*N1*N2*N3/(N1*N2+N2*N3+N1*N3)*;
MUOS:EMA(UOS,M);
;
;
;
2024-11-23 06:46
2024-11-23 06:19
2024-11-23 05:52
2024-11-23 05:25
2024-11-23 05:00