如何在Raspberry Pico上的第二个核心上运行代码

发布于 2025-01-26 23:25:01 字数 1621 浏览 3 评论 0原文

我正在尝试使多核心在我的PICO上工作,

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/multicore.h"

void core1_main()
{

    stdio_init_all();

    while (1)
    {
        uint32_t t = multicore_fifo_pop_blocking();
        printf("hellow world %d \n", t);
    }
}

int main()
{
    multicore_launch_core1(&core1_main);
    uint32_t i = 0;

    while (1)
    {
        sleep_ms(250);
        multicore_fifo_push_blocking(i++);
    }
}

这是我试图开始工作的非常基本的任务。我正在尝试了解有关这种多核魔术的更多信息。基本上,我正在开始等待core1,以获取一些数据。然后,我只需将其打印出来,然后等待下一个数据。 在核心0上,我每250ms一次将一个数字推到FIFO上。
我在编译中没有任何错误,但是运行代码不会产生任何输出。
我在这里做错了什么?我应该注意一些事情吗?

我已经尝试了很多东西来获得多核,但没有用。

更新 这给了我一些输出。 我添加了等待USB连接和初始化的等待。现在,我从Core 2收到一些消息。

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/multicore.h"

// const uint led = PICO_DEFAULT_LED_PIN;

void core1_main()
{
    printf("hellow world from second core");
    printf("hellow world from second core");
    printf("hellow world from second core");
}

int main()
{
    stdio_init_all();
    while (!stdio_usb_connected())
        ;
    while (!stdio_usb_init())
        ;

    multicore_launch_core1(core1_main);
    printf("hellow wow \n");

    uint32_t i = 0;

    while (1)
    {
        printf("hellow nice %d\n", i++);
        sleep_ms(1000);
    }
}

这是我获得的输出。请注意,来自第二核的消息仅通过一次。我很困惑,为什么?

同样,更改stdio_init_all()的位置会破坏某些内容,而不再输出。

I'm trying to get multicore working on my pico,

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/multicore.h"

void core1_main()
{

    stdio_init_all();

    while (1)
    {
        uint32_t t = multicore_fifo_pop_blocking();
        printf("hellow world %d \n", t);
    }
}

int main()
{
    multicore_launch_core1(&core1_main);
    uint32_t i = 0;

    while (1)
    {
        sleep_ms(250);
        multicore_fifo_push_blocking(i++);
    }
}

This is a very basic task I'm trying to get to work. I'm trying to learn more about this multicore magic. Basically I'm starting waiting on core1 for some data to come through. Then I simply print it out and wait for the next piece of data.
On core 0 I push a number onto the FIFO once every 250ms.
I don't get any error in compilation but running the code produces no output whatsoever.
What am I doing wrong here? Is there something that I should pat attention to?

I've tried quite a few things to get something multicore, but no use.

UPDATE
This gives me some output.
I added a wait for the USB to get connected and initialised. Now I get some message from core 2.

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/multicore.h"

// const uint led = PICO_DEFAULT_LED_PIN;

void core1_main()
{
    printf("hellow world from second core");
    printf("hellow world from second core");
    printf("hellow world from second core");
}

int main()
{
    stdio_init_all();
    while (!stdio_usb_connected())
        ;
    while (!stdio_usb_init())
        ;

    multicore_launch_core1(core1_main);
    printf("hellow wow \n");

    uint32_t i = 0;

    while (1)
    {
        printf("hellow nice %d\n", i++);
        sleep_ms(1000);
    }
}

This is the output I get. Notice the message from second core comes through only once.I confused, why?

Also changing the position of stdio_init_all() breaks something and no more output.

Output from minicom

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

陈甜 2025-02-02 23:25:01

我无法再现这个问题。我从您的代码的一个稍微修改的版本开始(我想要core1_main中的循环,这样我就不会在连接到串行端口之前错过输出):

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/multicore.h"

void core1_main()
{
    while (1) {
        printf("hello world from second core\n");
        sleep_ms(1000);
    }
}

int main()
{
    stdio_init_all();

    multicore_launch_core1(core1_main);
    printf("hello wow\n");

    uint32_t i = 0;

    while (1)
    {
        printf("hello nice %u\n", i++);
        sleep_ms(1000);
    }
}

我有以下cmakelists.txt,遵循pico sdk文档:

cmake_minimum_required(VERSION 3.13)

# initialize the SDK based on PICO_SDK_PATH
# note: this must happen before project()
include(pico_sdk_import.cmake)

project(my_project)

# initialize the Raspberry Pi Pico SDK
pico_sdk_init()

add_executable(multicore_test
    multicore_test.c
)

target_link_libraries(multicore_test pico_stdlib pico_multicore)

pico_enable_stdio_usb(multicore_test 1)
pico_enable_stdio_uart(multicore_test 0)


pico_add_extra_outputs(multicore_test)

如果构建代码:

mkdir build
cd build
cmake ..
make

然后将结果multicore_test.uf2安装到pico上,当我连接到串行端口时(/dev/dev/我的系统上的ttyacm0),我看到:

hello world from second core
hello nice 3
hello world from second core
hello nice 4
hello world from second core
hello nice 5
hello world from second core
hello nice 6
...

I cannot reproduce this problem. I started with a slightly modified version of your code (I wanted a loop in core1_main so that I didn't miss output before connecting to the serial port):

#include <stdio.h>
#include "pico/stdlib.h"
#include "pico/multicore.h"

void core1_main()
{
    while (1) {
        printf("hello world from second core\n");
        sleep_ms(1000);
    }
}

int main()
{
    stdio_init_all();

    multicore_launch_core1(core1_main);
    printf("hello wow\n");

    uint32_t i = 0;

    while (1)
    {
        printf("hello nice %u\n", i++);
        sleep_ms(1000);
    }
}

I have the following CMakeLists.txt, following the pico sdk documentation:

cmake_minimum_required(VERSION 3.13)

# initialize the SDK based on PICO_SDK_PATH
# note: this must happen before project()
include(pico_sdk_import.cmake)

project(my_project)

# initialize the Raspberry Pi Pico SDK
pico_sdk_init()

add_executable(multicore_test
    multicore_test.c
)

target_link_libraries(multicore_test pico_stdlib pico_multicore)

pico_enable_stdio_usb(multicore_test 1)
pico_enable_stdio_uart(multicore_test 0)


pico_add_extra_outputs(multicore_test)

If I build the code:

mkdir build
cd build
cmake ..
make

And then install the resulting multicore_test.uf2 onto the Pico, when I connect to the serial port (/dev/ttyACM0 on my system), I see:

hello world from second core
hello nice 3
hello world from second core
hello nice 4
hello world from second core
hello nice 5
hello world from second core
hello nice 6
...
太阳男子 2025-02-02 23:25:01

问题在于,您正在尝试通过调用stdio_init_all();在核心1。move

stdio_init_all(); core 0来 初始化TinyUSB堆栈。 。

这也是@larsks没有看到问题的原因。他将stdio_init_all();放在核心0上。

The issue is that you are trying to initialize the TinyUSB stack by calling stdio_init_all(); on core 1.

Move stdio_init_all(); to core 0. That will fix the issue.

That is also why @larsks didn't see the issue. He placed stdio_init_all(); on core 0.

以酷 2025-02-02 23:25:01

我遇到了完全相同的问题。旋转核心1,几秒钟后,它就停止了。我的代码看起来像这样:

void main2() {
    printf("Entered core1 (core=%d)\n", get_core_num());

    while(1) {        
        printf("ping (core=%d)\n", get_core_num());        
        sleep_ms(1000);
    }
}

int main() {
    stdio_init_all();

    printf("Entered core0 (core=%d)\n", get_core_num());

    multicore_launch_core1(main2);    

    while(1) {
        printf("ping (core=%d)\n", get_core_num());
        sleep_ms(1000);
    }
}

我得到的输出是:

Entered core0 (core=0)
ping (core=0)
Entered core1 (core=1)
ping (core=1)
ping (core=0)
ping (core=0)
ping (core=0)
ping (core=0)
ping (core=0)
ping (core=0)
...

Core 1打印了一个,有时几次,然后停止。问题的解决方案是在stdio_init_all()之后入睡。

void main2() {
    printf("Entered core1 (core=%d)\n", get_core_num());

    while(1) {        
        printf("ping (core=%d)\n", get_core_num());        
        sleep_ms(1000);
    }
}

int main() {
    stdio_init_all();

    // There isn't a strict rule that you must always call sleep_ms()
    // after stdio_init_all(). However, in some cases, it can be a helpful
    // precautionary measure to ensure that the UART has properly 
    // initialized and is ready to transmit data without any issues.
    sleep_ms(2000);

    printf("Entered core0 (core=%d)\n", get_core_num());

    multicore_launch_core1(main2);    

    while(1) {
        printf("ping (core=%d)\n", get_core_num());
        sleep_ms(1000);
    }
}

我在不睡觉的情况下多次尝试()。没有它,我总是会遇到问题,并且问题总是消失。

我没有一个人弄清楚这个,但问了Chatgpt。它告诉我:

没有一个严格的规则,您必须始终在stdio_init_all()之后始终致电Sleep_ms()。但是,在某些情况下,这可能是一项有用的预防措施,以确保UART已正确初始化并准备传输数据而无需任何问题。

但是它拒绝告诉我在哪里记录了这一点。我搜索了它,但没有找到有关它的其他信息。我确定它在那里,我看上去并不难。

I had the exact same problem. Spinning up core 1 and after a few seconds it just stopped. My code looked like this:

void main2() {
    printf("Entered core1 (core=%d)\n", get_core_num());

    while(1) {        
        printf("ping (core=%d)\n", get_core_num());        
        sleep_ms(1000);
    }
}

int main() {
    stdio_init_all();

    printf("Entered core0 (core=%d)\n", get_core_num());

    multicore_launch_core1(main2);    

    while(1) {
        printf("ping (core=%d)\n", get_core_num());
        sleep_ms(1000);
    }
}

And the output I got was:

Entered core0 (core=0)
ping (core=0)
Entered core1 (core=1)
ping (core=1)
ping (core=0)
ping (core=0)
ping (core=0)
ping (core=0)
ping (core=0)
ping (core=0)
...

Core 1 printed one, sometimes a couple of times and then stopped. The solution to the problem was to sleep after stdio_init_all().

void main2() {
    printf("Entered core1 (core=%d)\n", get_core_num());

    while(1) {        
        printf("ping (core=%d)\n", get_core_num());        
        sleep_ms(1000);
    }
}

int main() {
    stdio_init_all();

    // There isn't a strict rule that you must always call sleep_ms()
    // after stdio_init_all(). However, in some cases, it can be a helpful
    // precautionary measure to ensure that the UART has properly 
    // initialized and is ready to transmit data without any issues.
    sleep_ms(2000);

    printf("Entered core0 (core=%d)\n", get_core_num());

    multicore_launch_core1(main2);    

    while(1) {
        printf("ping (core=%d)\n", get_core_num());
        sleep_ms(1000);
    }
}

I tried multiple times with and without sleep(). Without it I always got the problem and with it the problem always went away.

I didn't figure this one out by myself but asked ChatGPT. It told me:

There isn't a strict rule that you must always call sleep_ms() after stdio_init_all(). However, in some cases, it can be a helpful precautionary measure to ensure that the UART has properly initialized and is ready to transmit data without any issues.

But it refused to tell me where this was documented. I googled it, but didn't find any other information about it. I am sure it is out there, I didn't look that hard.

薔薇婲 2025-02-02 23:25:01

STDIO最有可能对多线程不安全。

添加stdio_flush();在core1_main()的末尾可能会有所帮助。

例如,在stdio_init_all()之后等待一段时间也是建议:
while(!stdio_usb_connected()){sleep_ms(100);} //等到连接USB序列客户端/主机

Most likely stdio is not safe for multithreading.

Adding stdio_flush(); at the end of core1_main() could help.

Waiting a while after stdio_init_all() is also advicable for example:
while (!stdio_usb_connected()) {sleep_ms(100);} // wait until usb serial client/host is connected

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文