正在计划把内核开放出来,目前正在测试中,请耐心等待
C
chshwei
@chshwei
2
Reputation
9
Posts
4
Profile views
0
Followers
0
Following
Best posts made by chshwei
Latest posts made by chshwei
-
RE: 「RVBoards-哪吒」D1 Debian系统镜像和安装方法
@aixb 请重新下载镜像制作,现在已扩展到10GB,可以满足大部分人的需求,后续会推出自动扩展内存空间的版本,谢谢反馈
-
RVBoards-D1内存 1GB不够怎么办,交换 ”文件/分区" 为你解忧
一、基础知识
SWAP就是LINUX下的虚拟内存分区,它的作用是在物理内存使用完之后,将磁盘空间(也就是SWAP分区)虚拟成内存来使用. 它和Windows系统的交换文件作用类似,但是它是一段连续的磁盘空间,并且对用户不可见。 需要注意的是,虽然这个SWAP分区能够作为"虚拟"的内存,但它的速度比物理内存可是慢多了, 因此如果需要更快的速度的话,并不能寄厚望于SWAP,最好的办法仍然是加大物理内存.SWAP分区只是临时的解决办法. linux下得分区推荐一个交换分区,一个根分区,其中交换分区如上所说作为redhat或者其它虚机所划分的内存不够时候来使用! 交换分区(swap)的合理值一般在内存的2 倍左右,可以适当加大。 实际上具体还是以实际应用为准,swap为内存的2倍也不过是一种以讹传讹的说法。 如果交换分区的使用都超过4GB以上了,可想而知服务器的性能应该差很多了。 Linux下可以创建两种类型的交换空间,一种是swap分区,一种是swap文件。 前者适合有空闲的分区可以使用,后者适合于没有空的硬盘分区,硬盘的空间都已经分配完毕。
二、创建交换文件
在d1开发板上直接运行以下命令 #1、在根目录创建交换文件swapfile,bs为块大小,count为块的数量 sudo dd if=/dev/zero of=/swapfile bs=64M count=16 #2、格式化交换文件 sudo mkswap /swapfile #3、挂载交换文件 sudo swapon /swapfile #如果,不再使用交换文件,如下卸载并删除 #4、卸载交换文件 sudo swapoff /swapfile #5、删除交换文件 sudo rm /swapfile #top命令查看交换文件是否生效 top - 10:57:07 up 11 min, 1 user, load average: 1.00, 1.08, 0.80 Tasks: 93 total, 1 running, 92 sleeping, 0 stopped, 0 zombie %Cpu(s): 0.3 us, 0.3 sy, 0.0 ni, 99.3 id, 0.0 wa, 0.0 hi, 0.0 si, 0.0 st MiB Mem : 992.7 total, 67.3 free, 140.3 used, 785.1 buff/cache #"*************MiB Swap表示交换文件使用情况**************" MiB Swap: 1024.0 total, 1024.0 free, 0.0 used. 831.7 avail Mem PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND 794 root 20 0 7044 2828 2252 R 1.0 0.3 0:04.21 top 641 root 20 0 18084 3904 1612 S 0.7 0.4 0:03.06 systemd+ 118 root 20 0 18084 5236 2960 S 0.3 0.5 0:01.90 systemd+ 143 avahi 20 0 5028 2696 2272 S 0.3 0.3 0:01.44 avahi-d+ 623 root -2 0 0 0 0 S 0.3 0.0 0:00.33 xradio_+
三、创建交换分区
#注:请提前对sd卡进行备件,防止数据丢失 下面分区方式仅适用于RVBoards_D1_Debianv_img_v0.5镜像 , 删除原sd卡mmcblk0p6分区,新建swap分区和新的扩展存储分区 原sd卡mmcblk0p6分区是扩展存储分区,不会影响系统运行
[email protected]:~# fdisk -l #fdisk -l查看分区信息 Disk /dev/mmcblk0: 29.72 GiB, 31914983424 bytes, 62333952 sectors Units: sectors of 1 * 512 = 512 bytes Sector size (logical/physical): 512 bytes / 512 bytes I/O size (minimum/optimal): 512 bytes / 512 bytes Disklabel type: gpt Disk identifier: AB6F3888-569A-4926-9668-80941DCB40BC Device Start End Sectors Size Type /dev/mmcblk0p1 41464 47549 6086 3M Microsoft basic data /dev/mmcblk0p2 47550 48053 504 252K Microsoft basic data /dev/mmcblk0p3 48054 48557 504 252K Microsoft basic data /dev/mmcblk0p4 49152 251903 202752 99M Microsoft basic data /dev/mmcblk0p5 253358 10739117 10485760 5G Microsoft basic data /dev/mmcblk0p6 10739712 62333948 51594237 24.6G Linux filesystem
[email protected]:~# fdisk /dev/mmcblk0 #利用fdisk 命令对sd卡重新分区 Welcome to fdisk (util-linux 2.36.1). Changes will remain in memory only, until you decide to write them. Be careful before using the write command. Command (m for help): d #输入’d‘,删除第6分区 Partition number (1-6, default 6): 6 #输入’6‘,删除第6分区 Partition 6 has been deleted. Command (m for help): n #输入’n‘,新建分区 Partition number (6-8, default 6): 6 #输入’6‘,新建6分区 First sector (48558-62333948, default 10739712): #输入’回车‘,选择默认启始位置 #输入分区大小 Last sector, +/-sectors or +/-size{K,M,G,T,P} (10739712-62333948, default 62333948): 30000000 Created a new partition 6 of type 'Linux filesystem' and of size 9.2 GiB. Command (m for help): n #输入’n‘,新建分区 Partition number (7,8, default 7): #输入’7‘,新建7分区 First sector (48558-62333948, default 30001152): #输入’回车‘,选择默认启始位置 #输入分区大小,直接输入“回车”,默认大小 Last sector, +/-sectors or +/-size{K,M,G,T,P} (30001152-62333948, default 62333948): Created a new partition 7 of type 'Linux filesystem' and of size 15.4 GiB. Command (m for help): w #输入’w‘,完成分区,写入并退出 The partition table has been altered. Syncing disks.
[email protected]:~# fdisk -l #查看新分区信息 Disk /dev/mmcblk0: 29.72 GiB, 31914983424 bytes, 62333952 sectors Units: sectors of 1 * 512 = 512 bytes Sector size (logical/physical): 512 bytes / 512 bytes I/O size (minimum/optimal): 512 bytes / 512 bytes Disklabel type: gpt Disk identifier: AB6F3888-569A-4926-9668-80941DCB40BC Device Start End Sectors Size Type /dev/mmcblk0p1 41464 47549 6086 3M Microsoft basic data /dev/mmcblk0p2 47550 48053 504 252K Microsoft basic data /dev/mmcblk0p3 48054 48557 504 252K Microsoft basic data /dev/mmcblk0p4 49152 251903 202752 99M Microsoft basic data /dev/mmcblk0p5 253358 10739117 10485760 5G Microsoft basic data /dev/mmcblk0p6 10739712 30000000 19260289 9.2G Linux filesystem /dev/mmcblk0p7 30001152 62333948 32332797 15.4G Linux filesystem
[email protected]:~# mkswap /dev/mmcblk0p6 #格式化交换分区 Setting up swapspace version 1, size = 9.2 GiB (9861263360 bytes) no label, UUID=a38e9d65-5619-4ec5-b9cb-5547da777295 [email protected]:~# mkfs.ext4 /dev/mmcblk0p7 #格式化扩展存储分区 mke2fs 1.46.2 (28-Feb-2021) Creating filesystem with 4041599 4k blocks and 1011840 inodes Filesystem UUID: 63494eb8-ffed-43fd-a630-d8a8c5c3397d Superblock backups stored on blocks: 32768, 98304, 163840, 229376, 294912, 819200, 884736, 1605632, 2654208 Allocating group tables: done Writing inode tables: done Creating journal (16384 blocks): done Writing superblocks and filesystem accounting information: done
#编辑 /etc/fstab,挂载交换分区和存储分区 [email protected]:~# vim /etc/fstab # UNCONFIGURED FSTAB FOR BASE SYSTEM /dev/mmcblk0p5 / ext4 rw 0 1 /dev/mmcblk0p6 swap swap defautls 0 0 /dev/mmcblk0p7 /mnt ext4 rw 0 2 #重启后,用top命令查看交换分区是是否生效 [email protected]:~# top #MiB Swap表示交换文件使用情况 top - 12:38:23 up 1 min, 1 user, load average: 3.01, 1.09, 0.39 Tasks: 100 total, 1 running, 99 sleeping, 0 stopped, 0 zombie %Cpu(s): 1.0 us, 1.0 sy, 0.0 ni, 88.3 id, 9.7 wa, 0.0 hi, 0.0 si, 0.0 st MiB Mem : 992.7 total, 679.9 free, 139.9 used, 172.9 buff/cache 'MiB Swap: 9404.4 total, 9404.4 free, 0.0 used. 832.1 avail Mem ' PID USER PR NI VIRT RES SHR S %CPU %MEM TIME+ COMMAND 205 avahi 20 0 5028 2708 2296 S 1.0 0.3 0:00.26 avahi-d+ 59 root -51 0 0 0 0 S 0.7 0.0 0:01.02 irq/56-+ 725 root 20 0 7044 2868 2288 R 0.7 0.3 0:00.09 top 554 root 20 0 18092 5476 3184 S 0.3 0.5 0:00.37 systemd+ 1 root 20 0 94772 8500 6012 S 0.0 0.8 0:03.08 systemd 2 root 20 0 0 0 0 S 0.0 0.0 0:00.00 kthreadd 3 root 0 -20 0 0 0 I 0.0 0.0 0:00.00 rcu_gp
-
RE: 开发第一步就卡住了,是网络原因还是?
使用date命令更新下系统时间,默认系统时间不对,apt update会出错
-
RE: 这个kernel调试打印可以去掉,否则i2cdetect格式不对
@qhddz 请问是您自己写的驱动吗?出现这样的信息可能是您驱动有问题,i2c发送失败导致的,请查检您的驱动程序或设备是否存在问题
-
RE: 关于PLIC中断
没有与你要求相同的demo,你可以参考mini_car的中定时器中断设置的代码,配置按键中断,下面代码是mini_car的,仅供参考
// See LICENSE for license details. /************************************************************** ** 作者: Alvin Xu of PerfXLab ** 本程序展示了蜂鸟的PWM功能,蜂鸟中定义了PWM0、PWM1、PWM2三个PWM控制寄存器,每个PWMx可以输出 ** 4路PWM波,所以最多可以提供12路PWM波输出。本程序用到了PWM1的4路PWM波输出 ** ** 引脚硬件连接 ** PWM输出,本程序用到了D3和D4输出 ** PWM1_0用PWM_CMP0控制占空比,对应D4引脚(20) ** PWM1_1用PWM_CMP1控制占空比,对应D3_SCL引脚(19) ** PWM1_2用PWM_CMP2控制占空比,对应D5引脚(21) ** PWM1_3用PWM_CMP3控制占空比,对应D6引脚(22) ** ** 红外信号(left) ------------> D0 ** 红外信号(right) ------------> D1 ** ** 电机驱动模块 开发板 ** IN1 ------------> D8 ** IN2 ------------> D9 ** IN3 ------------> D10 ** IN4 ------------> D11 ** ENA ------------> D3_SCL ** ENB ------------> D4 ** **舵机信号线 ------------> D5 ** **超声波收发模块 开发板 **引脚 Trig ------------> A0 **引脚 Echo ------------> A1 **引脚 Vcc ------------> 5V VCC **引脚 Gnd ------------> GND **************************************************************/ /********************************************************************** ** 程序修改记录: ** 2018-8-1 ** 1、修改了hifive1.h内的智能车的宏定义,直接在主程序文件里面写了新的宏定义 ** 2、备注了定时器内的模拟pwm波的代码,添加了硬件pwm代码 ** 2018-8-7 ** 1、程序目前可以实现循迹功能、超声波测距回显、超声波控制小车启停的功能 ** 2、接下来需要添加一路PWM,控制舵机旋转 D5引脚输出控制舵机的PWM ** 2018-8-8 ** 1、要求实现的功能: **当小车靠近墙壁的时候,超声波检测到距离过近,停止小车前进,测量左边和右边的距离,比较两者,选择向距离大的一边转弯。 **需要添加的代码: **(1)左转弯90度(2)右转弯90度(3)当小车靠近墙壁的时候,对多舵机和超声波以及直流电机的组合操作 **2、设计程序 **3、添加了void motor_right()、void motor_left()、void motor_stop()函数。并且测试完毕,可以实现90度的转弯 **4、添加了void ultrasonic_control()函数,内部的逻辑编写完毕,等待配件到达后组装测试 ***********************************************************************/ //========================== smart-car-gpio===========================// #define run 1 #define stop 0 #define left_monitor D0_RX1 #define right_monitor D1_TX1 #define car_motor_IN1 D8 #define car_motor_IN2 D9 #define car_motor_IN3 D10 #define car_motor_IN4 D11 #define car_motor_ENA D3_SCL #define car_motor_ENB D4 #define servo_motor D5//控制舵机 输出PWM的引脚 //2018-8-7 #define servo_motor_right PWM1_REG(PWM_CMP2) = 0xffff/1000*125; // PWM高电平为0.5ms 舵机为0度 #define servo_motor_middle PWM1_REG(PWM_CMP2) = 0xffff/1000*125*3;// PWM高电平为1.5ms 舵机为90度 #define servo_motor_left PWM1_REG(PWM_CMP2) = 0xffff/1000*125*5;// PWM高电平为2.5ms 舵机为180度 //2018-8-8 #define left_monitor_run_fast PWM1_REG(PWM_CMP1) = 0xffff/9*4 // 4/9 PWM #define right_monitor_run_fast PWM1_REG(PWM_CMP0) = 0xffff/9*4 // 4/9 PWM #define left_monitor_run PWM1_REG(PWM_CMP1) = 0xffff/9*2 // 2/9 PWM #define right_monitor_run PWM1_REG(PWM_CMP0) = 0xffff/9*2 // 2/9 PWM #define left_monitor_stop PWM1_REG(PWM_CMP1) = 0 #define right_monitor_stop PWM1_REG(PWM_CMP0) = 0 //===================================================================// #include <stdio.h> #include <stdlib.h> #include "platform.h" #include <string.h> #include "plic/plic_driver.h" #include "encoding.h" #include <unistd.h> #include "stdatomic.h" void reset_demo (void); uint32_t GPIO_SET(uint32_t pin_num,uint32_t pin_val,uint32_t pin_model); void smartcar_init(void); void tracking_car_control(void); uint32_t read_pin_val(uint32_t pin_num); int delay_us(uint32_t time_x); void PWM_init(); volatile void wait_ms(uint64_t ms); float ultrasonic(void); void ultrasonic_control(); void motor_right(); void motor_left(); void motor_run(); void motor_stop(); void motor_back(); void motor_forward(); volatile int ultrasonic_run = 1;//超声波检测标志 //================================================================= // Structures for registering different interrupt handlers // for different parts of the application. typedef void (*function_ptr_t) (void); void no_interrupt_handler (void) {}; function_ptr_t g_ext_interrupt_handlers[PLIC_NUM_INTERRUPTS]; // Instance data for the PLIC. plic_instance_t g_plic; //****************************************************************** //函数名: wait_ms() //作者: Alvin Xu of PerfXLab //日期: 2018-08-01 //功能: 调用一次产生ms毫秒的软件延时 //输入参数:ms :毫秒数 //返回值: 无 //修改记录:无 //****************************************************************** volatile void wait_ms(uint64_t ms)//busy wait for the specified time { static const uint64_t ms_tick = RTC_FREQ/1000; volatile uint64_t * mtime = (uint64_t*) (CLINT_CTRL_ADDR + CLINT_MTIME); uint64_t then = (ms_tick * ms) + *mtime; while(*mtime<then); } //****************************************************************** //函数名: reset_demo //作者: PerfXLab //日期: 2018-07-04 //功能: 定时器初始化程序 //输入参数:无 //返回值: 无 //修改记录:无 //****************************************************************** void reset_demo () { // Disable the machine & timer interrupts until setup is done. clear_csr(mie, MIP_MEIP); clear_csr(mie, MIP_MTIP); for (int ii = 0; ii < PLIC_NUM_INTERRUPTS; ii ++) { g_ext_interrupt_handlers[ii] = no_interrupt_handler; } // Set the machine timer to go off in 0.01 seconds. // The volatile uint64_t * mtime = (uint64_t*) (CLINT_CTRL_ADDR + CLINT_MTIME); volatile uint64_t * mtimecmp = (uint64_t*) (CLINT_CTRL_ADDR + CLINT_MTIMECMP); uint64_t now = *mtime; uint64_t then = now + 0.1*RTC_FREQ; *mtimecmp = then; // Enable the Machine-External bit in MIE set_csr(mie, MIP_MEIP); // Enable the Machine-Timer bit in MIE set_csr(mie, MIP_MTIP); // Enable interrupts in general. set_csr(mstatus, MSTATUS_MIE); } //****************************************************************** //函数名: GPIO_SET //作者: PerfXLab //日期: 2018-07-04 //功能: 配置蜂鸟的引脚 //输入参数:pin_num:引脚名 // pin_val:引脚值,1或0 // pin_model:引脚模式,写input表示输入,写output表示输出 //返回值: 无 //修改记录:无 //****************************************************************** uint32_t GPIO_SET(uint32_t pin_num,uint32_t pin_val,uint32_t pin_model) { uint32_t input_val; if(pin_model==output) { GPIO_REG(GPIO_OUTPUT_EN) |= (0x01<<pin_num); if(pin_val==1) { GPIO_REG(GPIO_OUTPUT_VAL) |=(0x01<<pin_num); } if(pin_val==0) { GPIO_REG(GPIO_OUTPUT_VAL) &=~(0x01<<pin_num); } } if(pin_model==input) { GPIO_REG(GPIO_INPUT_EN) |= (0x01<<pin_num); input_val=GPIO_REG(GPIO_INPUT_VAL) &(0x01<<pin_num); if(input_val!=0) { input_val=1; }else { input_val=0; } return input_val; } return 0; } //****************************************************************** //函数名: smartcar_control //作者: PerfXLab //日期: 2018-07-04 //功能: 小车控制函数。实现小车的自动寻迹功能 //输入参数:无 //返回值: 无 //修改记录:无 //****************************************************************** void tracking_car_control() { uint32_t left_val,right_val; left_val=read_pin_val(left_monitor);//读取左边寻迹模块的检测信号 right_val=read_pin_val(right_monitor);//读取右边寻迹模块的检测信号 if(left_val==1) { right_monitor_run;//使能右边电机 } if(right_val==1) { left_monitor_run; //使能左边电机 } if(left_val==0) { right_monitor_stop;//失能右边电机 } if(right_val==0) { left_monitor_stop;//失能左边电机 } /*if(ultrasonic_run == 0) { motor_stop(); }*/ } //****************************************************************** //函数名: motor_stop //作者: PerfXLab //日期: 2018-07-04 //功能: 关闭小车的两个电机 //输入参数:无 //返回值: 无 //修改记录:无 //****************************************************************** void motor_stop() { right_monitor_stop; left_monitor_stop; } //****************************************************************** //函数名: motor_run //作者: PerfXLab //日期: 2018-07-04 //功能: 启动小车的两个电机 //输入参数:无 //返回值: 无 //修改记录:无 //****************************************************************** void motor_run() { right_monitor_run; left_monitor_run; } //****************************************************************** //函数名: motor_forward //作者: PerfXLab //日期: 2018-07-04 //功能: 实现小车车轮向后转 //输入参数:无 //返回值: 无 //修改记录:无 //****************************************************************** void motor_forward() //可以通过修改延时时间或者输出pwm波的占空比来调整转弯的角度 //目前调用一次可以原地 向左 旋转90度左右 { //左轮前转 GPIO_SET(car_motor_IN1 ,0,output); GPIO_SET(car_motor_IN2 ,1,output); //右轮前转 GPIO_SET(car_motor_IN3 ,0,output); GPIO_SET(car_motor_IN4 ,1,output); motor_run(); } //****************************************************************** //函数名: motor_back //作者: PerfXLab //日期: 2018-07-04 //功能: 实现小车车轮向后转 //输入参数:无 //返回值: 无 //修改记录:无 //****************************************************************** void motor_back() { //左轮后转 GPIO_SET(car_motor_IN1 ,1,output); GPIO_SET(car_motor_IN2 ,0,output); //右轮后转 GPIO_SET(car_motor_IN3 ,1,output); GPIO_SET(car_motor_IN4 ,0,output); motor_run(); } //****************************************************************** //函数名: motor_left //作者: PerfXLab //日期: 2018-07-04 //功能: 可以通过修改延时时间或者输出pwm波的占空比来调整转弯的角度 // 目前调用一次可以原地 向左 旋转90度左右 //输入参数:无 //返回值: 无 //修改记录:无 //****************************************************************** void motor_left() { //左轮后转 GPIO_SET(car_motor_IN1 ,1,output); GPIO_SET(car_motor_IN2 ,0,output); //右轮前转 GPIO_SET(car_motor_IN3 ,0,output); GPIO_SET(car_motor_IN4 ,1,output); right_monitor_run_fast; left_monitor_run_fast; wait_ms(300); motor_stop(); } //****************************************************************** //函数名: motor_right //作者: PerfXLab //日期: 2018-07-04 //功能: 可以通过修改延时时间或者输出pwm波的占空比来调整转弯的角度 // 目前调用一次可以原地 向右 旋转90度左右 //输入参数:无 //返回值: 无 //修改记录:无 //****************************************************************** void motor_right() { //左轮前转 GPIO_SET(car_motor_IN1 ,0,output); GPIO_SET(car_motor_IN2 ,1,output); //右轮后转 GPIO_SET(car_motor_IN3 ,1,output); GPIO_SET(car_motor_IN4 ,0,output); right_monitor_run_fast; left_monitor_run_fast; wait_ms(300); motor_stop(); } //****************************************************************** //函数名: ultrasonic //作者: PerfXLab //日期: 2018-07-04 //功能: 实现 超声波测距功能,并将距离返回到Serial Terminal //输入参数:无 //返回值: distance //修改记录:无 //****************************************************************** float distance=0; float ultrasonic() { uint64_t t1=0,t2=0; GPIO_SET(A1,0,input);//将A1配置为输入,接收超声波输入信号 GPIO_SET(A0,1,output); delay_us(1);//触发超声测距模块,产生12.4us的电平 GPIO_SET(A0,0,output); while( read_pin_val(A1) == 0 ); //A1输入为0时等待 t1 = get_timer_value(); while( read_pin_val(A1) == 1 );//A1输入为1时计数,测量高电平长度 t2 = get_timer_value(); distance =( (float)(t2-t1) )/RTC_FREQ*340/2; printf("%.2f厘米 \n \n",distance*100);//将测得的距离回传到Terminal里面显示 wait_ms(80); return distance; } //****************************************************************** //函数名: ultrasonic_control //作者: PerfXLab //日期: 2018-07-04 //功能: 超声波避障功能的控制逻辑 //输入参数:无 //返回值: 无 //修改记录:无 //****************************************************************** void ultrasonic_control() { ultrasonic();//触发超声波模块,并测量距离,给标志位置位(用led显示状态) float distance_left = 0, distance_right = 0; if( distance < 0.15 )//小于0.15米,停车 { motor_stop();//停车 GPIO_SET(ledD3,1,output); servo_motor_left; wait_ms(500); distance_left = ultrasonic(); wait_ms(500); servo_motor_right; wait_ms(500); distance_right = ultrasonic(); wait_ms(500); servo_motor_middle; if(distance_left >= distance_right) motor_left(); else motor_right(); motor_forward(); } else { GPIO_SET(ledD3,0,output); motor_run(); } } //****************************************************************** //函数名: PWM_init //作者: PerfXLab //日期: 2018-07-04 //功能: PWM功能的寄存器配置和初始化 //输入参数:无 //返回值: 无 //修改记录:无 //****************************************************************** void PWM_init() { //初始化PWM1寄存器为全0 PWM1_REG(PWM_CFG) = 0; //使能PWM1的4路PWM波 | 避免毛刺 | 计数器清零 | 配置计数器分频系数 PWM1_REG(PWM_CFG) = (PWM_CFG_ENALWAYS| PWM_CFG_DEGLITCH | PWM_CFG_ZEROCMP | 0xA); // PWM1_REG(PWM_COUNT) = 0; //选择IOF模式为IOF1 GPIO_REG(GPIO_IOF_SEL) |= ( (1 << car_motor_ENA) | (1 << car_motor_ENB) | (1 << servo_motor) ); //IOF使能,使io口可以输出PWM波 GPIO_REG(GPIO_IOF_EN ) |= (1 << car_motor_ENA) ; GPIO_REG(GPIO_IOF_EN ) |= (1 << car_motor_ENB); GPIO_REG(GPIO_IOF_EN ) |= (1 << servo_motor); //输出取反 GPIO_REG(GPIO_OUTPUT_XOR)|= ( (1 << car_motor_ENA) | (1 << car_motor_ENB) | (1 << servo_motor) ); //配置占空比 PWM1_REG(PWM_CMP0) = 0;//0% PWM 一个周期的时钟个数(分频后) 160000 PWM1_REG(PWM_CMP1) = 0;//0% PWM 0xffff/5 PWM1_REG(PWM_CMP2) = 0;//0% PWM高电平为5ms //配置输出频率为 244/8 Hz,频率最小可以到 244/(2^15) Hz //PWM1_REG(PWM_CFG) |= 0;//为原频率的 2的0次方 分之一 } //****************************************************************** //函数名: smartcar_init //作者: PerfXLab //日期: 2018-07-04 //功能: 小车Io口的初始化 //输入参数:无 //返回值: 无 //修改记录:无 //****************************************************************** void smartcar_init() { //超声距离检测指示端口灯初始化 GPIO_SET(ledD3,1,output); //初始化红外模块输出信号的接收端口 GPIO_SET(left_monitor ,0,input); GPIO_SET(right_monitor ,0,input); //确定电机方向向前行 GPIO_SET(car_motor_IN3 ,0,output); GPIO_SET(car_motor_IN4 ,1,output); GPIO_SET(car_motor_IN1 ,0,output); GPIO_SET(car_motor_IN2 ,1,output); } //****************************************************************** //函数名: read_pin_val //作者: PerfXLab //日期: 2018-07-04 //功能: 读输入引脚的电平 //输入参数:pin_num //返回值: 1或0 //修改记录:无 //****************************************************************** uint32_t read_pin_val(uint32_t pin_num) { if((GPIO_REG(GPIO_INPUT_VAL))&(0x01<<pin_num)) { return 1; } else return 0; } //****************************************************************** //函数名: delay_us //作者: PerfXLab //日期: 2018-07-04 //功能: time_x = 1 时产生12.4us的延时 //输入参数:time_x //返回值: 无 //修改记录:无 //****************************************************************** int delay_us(uint32_t time_x)//time_x = 1 时产生12.4us的延时 { volatile uint32_t num; //注意不要将volatile语句删除,否则编译器会自动优化掉延时函数,导致延时函数无法工作 num = 25*time_x; while(num>0) {num--;} return 0; } //==============以下两个函数是中断函数接口=====================================// /*Entry Point for PLIC Interrupt Handler*/ void handle_m_ext_interrupt() { plic_source int_num = PLIC_claim_interrupt(&g_plic); if ((int_num >=1 ) && (int_num < PLIC_NUM_INTERRUPTS)) { g_ext_interrupt_handlers[int_num](); } else { exit(1 + (uintptr_t) int_num); } PLIC_complete_interrupt(&g_plic, int_num); } /*Entry Point for Machine Timer Interrupt Handler*/ void handle_m_time_interrupt() { clear_csr(mie, MIP_MTIP); volatile uint64_t * mtime = (uint64_t*) (CLINT_CTRL_ADDR + CLINT_MTIME); volatile uint64_t * mtimecmp = (uint64_t*) (CLINT_CTRL_ADDR + CLINT_MTIMECMP); uint64_t now = *mtime; uint64_t then = now +0.1*RTC_FREQ; *mtimecmp = then; //ultrasonic(); // Re-enable the timer interrupt. set_csr(mie, MIP_MTIP); } //============================================================================// //============================================================================// // 主函数 //=============================================================================// int main(int argc, char **argv) { /************************************************************************** * Set up the PLIC *************************************************************************/ PLIC_init(&g_plic, PLIC_CTRL_ADDR, PLIC_NUM_INTERRUPTS, PLIC_NUM_PRIORITIES); GPIO_SET(ledD3,1,output); //测试端口初始化 smartcar_init(); //初始化相关端口 PWM_init(); //初始化PWM1 servo_motor_middle; //控制舵机使超声波模块面向向前方 motor_forward(); //使能直流电机,小车前进 while (1) { //两种功能可以选择使用 //方法是备注掉不用的那一行代码 ultrasonic_control(); //超声波避障功能 // tracking_car_control(); //循迹小车功能 } }