五、MicroPython移植到任意平台(math模块以及Qstr哈希值计算)

目录

note:本章内容依赖本专栏前几篇文章,若有疑问请先阅读本专栏前几篇文章。

一、math模块

1、math模块简介

二、math源码适配

1、math宏开关

2、注册math模块

三、Qstr哈希值计算

1、算法来源

2、计算新增关键字字符串的hash值

四、解决编译报错问题

1、编译问题

2、运行结果

五、总结


note:本章内容依赖本专栏前几篇文章,若有疑问请先阅读本专栏前几篇文章。

总目录如下:

MicroPython移植到任意平台_micropython 移植stm32-CSDN博客

一、math模块

1、math模块简介

math是python语言的数学库模块,包含常用的数学运算方法,例如 sin cos tan log等基本函数,本次打开math开关后,显示python接口如下图

二、math源码适配

1、math宏开关

在ports\minimal\mpconfigport.h中定义如下宏

#define MICROPY_PY_MATH                   (1)
#define MICROPY_PY_BUILTINS_FLOAT         (1)
#define MICROPY_FLOAT_IMPL                (2)

其中MICROPY_PY_MATH表示支持数学库,MICROPY_PY_BUILTINS_FLOAT表示支持浮点计算,MICROPY_FLOAT_IMPL表示支持双精度或单精度浮点。

2、注册math模块

在文件 genhdr\moduledefs.h 注册math模块

三、Qstr哈希值计算

1、算法来源

计算字符串的hash值,以便解释器通过此值快速识别脚本关键字,算法定义在py\qstr.c中

2、计算新增关键字字符串的hash值

我们每次增加自定义接口,意味着要增加关键字字符串,那么不可能每次去手动计算字符串的hash值(定义在genhdr\qstrdefs.generated.h中的字符串哈希表),比如我们要增加"XYB_BIN1","XYB_BIN2","XYB_BIN3"这几个字符串,根据我们提取的算法,得到C语言代码如下:

#include <stdio.h>
#include <string.h>

unsigned int qstr_compute_hash(const char *data, unsigned int len);

int main()
{
	#define STR_SIGNLE_LEN (50)
	const unsigned char str_group[][STR_SIGNLE_LEN] = 
	{
		"XYB_BIN1", "XYB_BIN2", "XYB_BIN3"
	};
	for(int i = 0; i < sizeof(str_group)/STR_SIGNLE_LEN; i++)
	{
		const unsigned char *str_p = str_group[i];
		const unsigned int str_len = strlen(str_p);
		if(str_len > 0)
		{
			unsigned int hash = qstr_compute_hash(str_p, str_len);
			unsigned char str_out[100] = {0};
			sprintf(str_out, "QDEF(MP_QSTR_%s, %d, %d, \"%s\")", str_p, hash, str_len, str_p);
			printf("%s\r\n", str_out);
		}
		else
		{
			break;
		}
	}
	return 0;
}

#define MICROPY_QSTR_BYTES_IN_HASH (2)

#define Q_HASH_MASK ((1 << (8 * MICROPY_QSTR_BYTES_IN_HASH)) - 1)

unsigned int qstr_compute_hash(const char *data, unsigned int len) {
    // djb2 algorithm; see http://www.cse.yorku.ca/~oz/hash.html
    unsigned int hash = 5381;
    for (const char *top = data + len; data < top; data++) {
        hash = ((hash << 5) + hash) ^ (*data); // hash * 33 ^ data
    }
    hash &= Q_HASH_MASK;
    // Make sure that valid hash is never zero, zero means "hash not computed"
    if (hash == 0) {
        hash++;
    }
    return hash;
}

在在线C语言工具(C 在线工具 | 菜鸟工具)中运行代码,结果如下图

我们将计算结果复制到genhdr\qstrdefs.generated.h中,就完成了python关键字的新增。

四、解决编译报错问题

1、编译问题

打开math模块的宏开关后,编译报如下Qstr字符串未定义错误:

有了第三章的铺垫,我们就知道,我们需要计算对应字符串(根据编译报错确定哪些字符串未定义)的hash值,如下图:

将计算结果复制到genhdr\qstrdefs.generated.h中去:

2、运行结果

根据编译报错解决编译问题后,下载运行,结果如下图所示:

五、总结

如有问题请指出,遇到解决不了的问题请私信或评论,感谢!

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值