找回密码
 立即注册
楼主: CosyOS

全局不关总中断的 RTOS,CosyOS-III-V1.2.0, 送 擎天柱-AI8051U转89C52核心板

 火... [复制链接]
  • 打卡等级:以坛为家I
  • 打卡总天数:345
  • 最近打卡:2025-06-15 11:58:42

0

主题

28

回帖

585

积分

高级会员

积分
585
发表于 2025-5-28 11:00:44 | 显示全部楼层
用AiCube生成的工程中,有printf字符发送重定向函数,编译没有报警错误。当升级为CosyOS工程时,编译时有错误提示。我仿照前面的CosyOS工程试例,单独建一个C文件,将putchar()函数放进来,然后在函数的上面复制这一句#pragma functions(static),这样再编译时就没有错误提示了。这是什么原因呢?
微信截图_20250528105238.png

点评

启用全局可重入:[attachimg]101758[/attachimg] [attachimg]101760[/attachimg] “1”是当启用全局可重入时,这些函数都声明了 static 属性,包括 putchar; “2”是未启用全局可重入时,这些函数都没有额外声明  详情 回复 发表于 2025-5-28 18:17
回复 支持 反对

使用道具 举报 送花

  • 打卡等级:以坛为家II
  • 打卡总天数:465
  • 最近打卡:2025-06-15 18:01:12

5

主题

1152

回帖

4473

积分

荣誉版主

积分
4473
发表于 2025-5-28 18:17:37 | 显示全部楼层
stc-x*** 发表于 2025-5-28 11:00
用AiCube生成的工程中,有printf字符发送重定向函数,编译没有报警错误。当升级为CosyOS工程时,编译时有错 ...

启用全局可重入: 截图202505281551084513.jpg

截图202505281605474956.jpg
“1”是当 C251版本 >= 2.00 时,这些函数都声明了 static 属性,包括 putchar;
“2”是当 C251版本 <   2.00 时,我们不必管它,因为我们现在用的版本都会大于2.00。

启用全局可重入后:
1、如果你的 putchar 不做更多修饰,默认为 reentrant 属性;
2、如果你的 putchar 所在的C文件中,包含了 stdio.h,你的 putchar 也必须定义为 static 属性,
否则,声明和定义不同,导致报错,
截图202505281737181186.jpg
3、如果你的 putchar 所在的C文件中,未包含 stdio.h,你的 putchar 无论是否定义为 static,都不会报错。
但是 你的 putchar 仍然必须定义为 static,否则它不会被编译。
因为 你的 putchar 未定义 static,不能满足使用要求,
此时 printf 仍然会调用 标准库中的 putchar,而非你的 putchar,
而后 你的 putchar 被 REMOVEUNUSED 移除掉了。

结论:
1、如果未启用全局可重入,用户的 putchar 可以普通定义方式,也可以定义 static 属性。
2、如果启用了全局可重入,用户的 putchar 必须 定义 static 属性。

方法1:
缺点是 putchar 之后的所有函数也一并定义了 static 属性。
#pragma functions(static)
char putchar(char c)
{

}

方法2:
只有 putchar 会被定义 static 属性,对后续其它函数无影响。
#pragma SAVE
#pragma functions(static)
char putchar(char c)
{

}
#pragma RESTORE




回复 支持 1 反对 0

使用道具 举报 送花

  • 打卡等级:以坛为家II
  • 打卡总天数:465
  • 最近打卡:2025-06-15 18:01:12

5

主题

1152

回帖

4473

积分

荣誉版主

积分
4473
发表于 2025-5-28 18:43:02 | 显示全部楼层
sdw*** 发表于 2025-5-27 17:44
/**
\brief      任务节点(控制块)
\details    CosyOS 的 任务节点 即 任务控制块,包含了任务所需的 ...

注意,在控制块结构体中,用 struct s_tasknode_ts 是在多次定义指针变量,而非实体。
这就是链表。。。
回复 支持 反对

使用道具 举报 送花

  • 打卡等级:以坛为家I
  • 打卡总天数:345
  • 最近打卡:2025-06-15 11:58:42

0

主题

28

回帖

585

积分

高级会员

积分
585
发表于 2025-5-29 23:48:30 | 显示全部楼层
我动态创建了2个任务,下载后不运行。但将任务改成静态创建后,却能正常运行。不知什么原因?后面附有工程文件。

stc32g-cosyos-led2.zip

2.55 MB, 下载次数: 7

点评

根本原因找到了,是 Starter 任务栈小了。 任务动态创建后,启动任务需要更大的任务栈,syscfg.h 中,把 Starter 任务栈 设置大一些就好了,不必再调整内存池指针。  详情 回复 发表于 2025-5-30 15:17
你只需适当调整一下内存池就可以了, 把内存池指针改小一点,哪怕改成“2716”都能跑起来。 关于这个问题的原因我需要再深入研究一下,恐怕没有那么简单。  详情 回复 发表于 2025-5-30 14:38
回复 支持 反对

使用道具 举报 送花

  • 打卡等级:以坛为家II
  • 打卡总天数:465
  • 最近打卡:2025-06-15 18:01:12

5

主题

1152

回帖

4473

积分

荣誉版主

积分
4473
发表于 2025-5-30 14:38:15 | 显示全部楼层
stc-x*** 发表于 2025-5-29 23:48
我动态创建了2个任务,下载后不运行。但将任务改成静态创建后,却能正常运行。不知什么原因?后面附有工程 ...

你只需适当调整一下内存池就可以了,
把内存池指针改小一点,哪怕改成“2716”都能跑起来。

关于这个问题的原因我需要再深入研究一下,恐怕没有那么简单。

回复 支持 反对

使用道具 举报 送花

  • 打卡等级:以坛为家II
  • 打卡总天数:465
  • 最近打卡:2025-06-15 18:01:12

5

主题

1152

回帖

4473

积分

荣誉版主

积分
4473
发表于 2025-5-30 15:17:33 | 显示全部楼层
stc-x*** 发表于 2025-5-29 23:48
我动态创建了2个任务,下载后不运行。但将任务改成静态创建后,却能正常运行。不知什么原因?后面附有工程 ...

根本原因找到了,是 Starter 任务栈小了。
任务动态创建后,启动任务需要更大的任务栈,
syscfg.h 中,把 Starter 任务栈 设置大一些就好了,不必再调整内存池指针。

截图202505301519154295.jpg
截图202505301521294014.jpg

回复 支持 反对

使用道具 举报 送花

  • 打卡等级:偶尔看看III
  • 打卡总天数:57
  • 最近打卡:2025-06-16 08:59:18
已绑定手机

0

主题

37

回帖

334

积分

中级会员

积分
334
发表于 2025-6-2 09:56:07 | 显示全部楼层
回复

使用道具 举报 送花

  • 打卡等级:以坛为家II
  • 打卡总天数:425
  • 最近打卡:2025-06-16 10:41:21
已绑定手机

12

主题

57

回帖

924

积分

高级会员

积分
924
发表于 2025-6-3 23:31:26 | 显示全部楼层
我是用usbcdc库添加usb_init()就出现L127,L128错误,注释掉后就能正常编译。单独使用usbcdc程序是正常的。想请教一下老师们这个问题怎么解决。

CosyOS-III.zip

4.67 MB, 下载次数: 2

回复 支持 反对

使用道具 举报 送花

  • 打卡等级:以坛为家II
  • 打卡总天数:425
  • 最近打卡:2025-06-16 10:41:21
已绑定手机

12

主题

57

回帖

924

积分

高级会员

积分
924
发表于 2025-6-4 18:27:06 | 显示全部楼层
一束光*** 发表于 2025-6-3 23:31
我是用usbcdc库添加usb_init()就出现L127,L128错误,注释掉后就能正常编译。单独使用usbcdc程序是正常的。 ...

自己回复一下,参考了论坛坛友的一个解决方法,如下图所示:
截图202506032330317750.jpg
截图202506041826537629.jpg

点评

这个问题的根源在于,在 Keil C251/A251 下,在不同条件下,汇编函数的命名法是不同的。 这些条件具体包括了 Code Rom Size(Large、Huge)、函数属性(reentrant、static)等, 它们将影响汇编函数的尾缀命名规则  详情 回复 发表于 2025-6-5 15:35
回复 支持 反对

使用道具 举报 送花

  • 打卡等级:以坛为家II
  • 打卡总天数:465
  • 最近打卡:2025-06-15 18:01:12

5

主题

1152

回帖

4473

积分

荣誉版主

积分
4473
发表于 2025-6-5 15:35:39 | 显示全部楼层
一束光*** 发表于 2025-6-4 18:27
自己回复一下,参考了论坛坛友的一个解决方法,如下图所示:

这个问题的根源在于,在 Keil C251/A251 下,在不同条件下,汇编函数的命名法是不同的。

这些条件具体包括了 Code Rom Size(Large、Huge)、函数属性(reentrant、static)等,
它们将影响汇编函数的尾缀命名规则。
总之在不同情况下,汇编函数名称后面可能需要添加不同的尾缀,如 ?  ??  ?_  等。

你遇到的问题,void usb_init(); 如此声明,那么在 lib中,汇编函数的名称已固定为 usb_init。
当启用全局可重入时,编译器会认为 void usb_init() 是一个reentrant函数,它的汇编函数名称
应为 usb_init?_,但实际上它在lib中是命名为 usb_init,所以才会报错 L127、L128,未解析的
外部模型,因为找不到 usb_init?_。

个人观点:对于 STC32,不启用全局可重入函数是愚蠢的行为,如非必要,还是启用为好,
这样会像ARM一样易用,因为不必再像51一样,凡是函数都要考虑会不会重入?是否可重入?等问题。

解决方法(前提还是要启用全局可重入函数):
截图202506051646397161.jpg
把 void usb_init(); 声明为 static属性,这样它的汇编函数名称仍为 usb_init,
这样问题完美解决


回复 支持 反对

使用道具 举报 送花

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|手机版|小黑屋|深圳国芯人工智能有限公司 ( 粤ICP备2022108929号-2 )

GMT+8, 2025-6-16 16:16 , Processed in 1.596813 second(s), 109 queries .

Powered by Discuz! X3.5

© 2001-2025 Discuz! Team.

快速回复 返回顶部 返回列表