사물 인터넷 (IoT)의 부상으로 프로그래밍 하드웨어가 더 보편화되었습니다. RT-Thread를 사용하면 FinSH를 사용하여 Linux 명령 줄에서 장치에 연결할 수 있습니다.
https://opensource.com/article/20/9/hardware-command-line
RT-Thread는 IoT (사물 인터넷) 기기를 프로그래밍 하는 데 사용되는 오픈 소스 실시간 운영체제입니다. FinSH는 RT-Thread의 명령 줄 구성 요소이며 사용자가 명령 줄에서 장치에 연결할 수 있도록 일련의 운영 인터페이스를 제공합니다. 주로 시스템 정보를 디버그 하거나 보는 데 사용됩니다.
일반적으로 개발 디버깅은 하드웨어 디버거 및 printf 로그를 사용하여 표시됩니다. 그러나 어떤 경우에는 이 두 가지 방법이 실행 중인 항목에서 추상화되어 구문 분석이 어려울 수 있기 때문에 그다지 유용하지 않습니다. RT-Thread는 다중 스레드 시스템이지만 실행 중인 스레드의 상태 나 수동 제어 시스템의 현재 상태를 알고 싶을 때 유용합니다.
다중 스레드이기 때문에 대화 형 셸을 가질 수 있으므로 명령을 입력하거나 장치에서 직접 함수를 호출하여 필요한 정보를 얻거나 프로그램의 동작을 제어 할 수 있습니다. Linux 또는 BSD와 같은 최신 운영 체제에만 익숙한 경우 일반적으로 보일 수 있지만 하드웨어 해커에게는 이것은 매우 사치스럽고 직렬 케이블을 보드에 직접 연결하여 오류를 엿보는 것과는 거리가 멀다.
FinSH에는 두 가지 모드가 있습니다.
C 언어 해석 모드에서 FinSH는 대부분의 C 언어를 실행하는 표현식을 구문 분석하고 함수 호출을 사용하여 시스템의 함수 및 전역 변수에 액세스 할 수 있습니다. 명령 줄에서 변수를 만들 수도 있습니다.
msh 모드에서 FinSH는 Bash와 같은 기존 셸과 유사하게 작동합니다.
GNU 명령 표준
FinSH를 개발할 때 명령 줄 응용 프로그램을 작성하기 전에 GNU 명령 줄 표준에 익숙해 져야 한다는 것을 배웠습니다. 이 표준 관행 프레임 워크는 인터페이스에 익숙해 지도록 하여 개발자가 사용시 편안함과 생산성을 느끼도록 도와줍니다.
완전한 GNU 명령은 네 가지 주요 부분으로 구성됩니다.
어떤 명령으로도 이를 확인할 수 있습니다. Git을 예로 들면 :
git reset --hard HEAD~1
다음과 같이 분류됩니다.
실행 가능한 명령은 git, 하위 명령은 재설정, 사용 된 옵션은 --head, 인수는 HEAD ~ 1입니다.
다른 예시:
systemctl enable --now firewalld
실행 가능한 명령은 systemctl, 하위 명령은 enable, 옵션은 --now, 인수는 firewalld입니다.
RT-Thread를 사용하여 GNU 표준을 준수하는 명령 줄 프로그램을 작성하고 싶다고 상상해보십시오. FinSH는 필요한 모든 것을 갖추고 있으며 예상대로 코드를 실행합니다. 더 좋은 점은 이 규정 준수에 의존하여 좋아하는 Linux 프로그램을 자신 있게 이식 할 수 있다는 것입니다.
우아한 명령 줄 프로그램 작성
다음은 RT-Thread 개발자가 매일 사용하는 명령을 실행하는 RT-Thread의 예입니다.
usage: env.py package [-h] [--force-update] [--update] [--list] [--wizard]
[--upgrade] [--printenv]
optional arguments:
-h, --help show this help message and exit
--force-update force update and clean packages, install or remove the
packages by your settings in menuconfig
--update update packages, install or remove the packages by your
settings in menuconfig
--list list target packages
--wizard create a new package with wizard
--upgrade upgrade local packages list and ENV scripts from git repo
--printenv print environmental variables to check
아시다시피 친숙한 것처럼 보이며 이미 Linux 또는 BSD에서 실행 중인 대부분의 POSIX 응용 프로그램처럼 작동합니다. 부정확하거나 불충분 한 구문을 사용하고 길고 짧은 옵션을 모두 지원하며 일반적인 사용자 인터페이스는 Unix 터미널을 사용하는 모든 사람에게 친숙한 경우에 도움말이 제공됩니다.
옵션의 종류
다양한 종류의 옵션이 있으며 길이에 따라 두 가지 주요 범주로 나눌 수 있습니다.
이러한 옵션은 인수가 있는지 여부에 따라 세 가지 범주로 나눌 수 있습니다.
대부분의 Linux 명령에서 예상 할 수 있듯이 FinSH 옵션 구문 분석은 매우 유연합니다. 공백이나 등호를 구분 기호로 사용하거나 옵션 자체를 추출하고 뒤에 오는 것이 인수라고 가정하여 옵션을 인수와 구분할 수 있습니다 (즉, 구분 기호가 전혀 없음).
optparse 사용
명령 줄 응용 프로그램을 작성한 적이 있다면 일반적으로 optparse라는 선택한 언어에 대한 라이브러리 또는 모듈이 있음을 알 수 있습니다. 프로그래머에게 제공되므로 명령의 일부로 입력 된 옵션 (예 : -v 또는 --verbose)을 나머지 명령과 관련하여 구문 분석 할 수 있습니다. 코드가 하위 명령 또는 인수의 옵션을 인식하는 데 도움이 됩니다.
FinSH에 대한 명령을 작성할 때 optparse 패키지는 다음 형식을 예상합니다.
MSH_CMD_EXPORT_ALIAS(pkgs, pkgs, this is test cmd.);
긴 형식이나 짧은 형식 또는 둘 다를 사용하여 옵션을 구현할 수 있습니다. 예를 들면 :
static struct optparse_long long_opts[] =
{
{"help" , 'h', OPTPARSE_NONE}, // Long command: help, corresponding to short command h, without arguments.
{"force-update", 0 , OPTPARSE_NONE}, // Long comman: force-update, without arguments
{"update" , 0 , OPTPARSE_NONE},
{"list" , 0 , OPTPARSE_NONE},
{"wizard" , 0 , OPTPARSE_NONE},
{"upgrade" , 0 , OPTPARSE_NONE},
{"printenv" , 0 , OPTPARSE_NONE},
{ NULL , 0 , OPTPARSE_NONE}
};
옵션을 만든 후 각 옵션과 해당 인수에 대한 명령과 지침을 작성합니다.
static void usage(void)
{
rt_kprintf("usage: env.py package [-h] [--force-update] [--update] [--list] [--wizard]\n");
rt_kprintf(" [--upgrade] [--printenv]\n\n");
rt_kprintf("optional arguments:\n");
rt_kprintf(" -h, --help show this help message and exit\n");
rt_kprintf(" --force-update force update and clean packages, install or remove the\n");
rt_kprintf(" packages by your settings in menuconfig\n");
rt_kprintf(" --update update packages, install or remove the packages by your\n");
rt_kprintf(" settings in menuconfig\n");
rt_kprintf(" --list list target packages\n");
rt_kprintf(" --wizard create a new package with wizard\n");
rt_kprintf(" --upgrade upgrade local packages list and ENV scripts from git repo\n");
rt_kprintf(" --printenv print environmental variables to check\n");
}
다음 단계는 구문 분석입니다. 아직 기능을 구현할 수는 없지만 구문 분석 된 코드의 프레임 워크는 동일합니다.
int pkgs(int argc, char **argv)
{
int ch;
int option_index;
struct optparse options;
if(argc == 1)
{
usage();
return RT_EOK;
}
optparse_init(&options, argv);
while((ch = optparse_long(&options, long_opts, &option_index)) != -1)
{
ch = ch;
rt_kprintf("\n");
rt_kprintf("optopt = %c\n", options.optopt);
rt_kprintf("optarg = %s\n", options.optarg);
rt_kprintf("optind = %d\n", options.optind);
rt_kprintf("option_index = %d\n", option_index);
}
rt_kprintf("\n");
return RT_EOK;
}
다음은 함수 헤드 파일입니다.
#include "optparse.h"
#include "finsh.h"
그런 다음 컴파일하고 장치에 다운로드하십시오.
하드웨어 해킹
프로그래밍 하드웨어는 위협적인 것처럼 보일 수 있지만 IoT로 인해 점점 더 보편화되고 있습니다. 모든 것이 Raspberry Pi에서 실행될 수 있거나 실행되어야 하는 것은 아니지만 RT-Thread를 사용하면 FinSH 덕분에 친숙한 Linux 느낌을 유지할 수 있습니다.
베어 메탈 코딩에 대해 궁금하다면 RT-Thread를 사용해보십시오.
등록된 댓글이 없습니다.