433发送模块硬件:载波要强劲(更换天线,电阻,引脚电压3.3V等),433芯片的第5引脚电压3.3v,程序跑起来如果低于3.3v,则载波的功率太低,发送的波形,接受端学习不到。第四脚可以通过示波器看到波形。
应用程序多线程里发送433的波形会被拉长,里面有usleep函数,尝试在应用层用popen函数和实时线程FIFO,发送5次,接收端才能收到一次,但有时会失败。所以把433发送端写成驱动,用内核udelay函数,发送时用内核自旋锁,每次发送波形都很漂亮,接受端都可以受到。
/kernel/xx_433/433.c如下:
/
#include <linux/miscdevice.h>
#include <linux/delay.h>
#include <asm/irq.h>
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/cdev.h>
#include <linux/fs.h>
#include <linux/uaccess.h>
#include <linux/errno.h>
#include <linux/device.h>
#include <linux/ioport.h>
#include <linux/io.h>
#include <linux/interrupt.h>
#include <linux/delay.h>
#include <linux/sched.h>
#include <linux/wait.h>
#include <asm/ioctl.h>
#include <linux/fs.h>
#include <linux/types.h>
#include <linux/spinlock.h>
#include <gpio.h>
#include <soc/gpio.h>
#include "xx_433.h"
#define DEVICE_NAME "433"
spinlock_t cache_lock;
void set_gpio(void)
{
//write(fd_v, "1", 1);
gpio_set_value(GPIO_433, 1);
}
void clean_gpio(void)
{
//write(fd_v, "0", 1);
gpio_set_value(GPIO_433, 0);
}
void send_one(void)
{
set_gpio();
udelay(1200);
clean_gpio();
udelay(400);
}
void send_zero(void)
{
set_gpio();
udelay(400);
clean_gpio();
udelay(1200);
}
static void send_byte(unsigned char dat)
{
unsigned char i;
for(i = 8; i > 0; i--)
{
if(dat & 0x80)
{
send_one();
}
else
{
send_zero();
}
dat = dat<<1;
}
}
void ask_send(unsigned char dat[], unsigned char len)
{
unsigned char i;
send_one();
udelay(13*1000); //15ms sync
for(i = 0; i < len; i++)
{
send_byte(dat[i]);
}
}
static long t433_ioctl(struct file *filp, unsigned int cmd, unsigned long arg)
{
unsigned long flags ;
unsigned char dat[16] = {0};
unsigned char *from = (unsigned char *)arg;
//static inline long copy_to_user(void __user *to,const void *from, unsigned long n)
copy_from_user(dat, from, strlen(from));
printk("cmd:%x, dat:%s\n", cmd, dat);
if(cmd == 1)
{
spin_lock_irqsave(&cache_lock, flags);
ask_send(dat, 3);
ask_send(dat, 3);
ask_send(dat, 3);
ask_send(dat, 3);
spin_unlock_irqrestore(&cache_lock, flags);
}
return 0;
}
#if 0 // test
static long t433_ioctl(struct file *filp, unsigned int cmd, unsigned int arg)
{
unsigned long flags ;
printk("cmd:%x, arg:%s\n", cmd, to);
char dat[3] = {0xf0, 0xf0, 0x07};
if(cmd == 1)
{
spin_lock_irqsave(&cache_lock, flags);
ask_send(dat, 3);
ask_send(dat, 3);
ask_send(dat, 3);
ask_send(dat, 3);
spin_unlock_irqrestore(&cache_lock, flags);
}
return 0;
}
#endif
static struct file_operations dev_fops = {
.owner = THIS_MODULE,
.unlocked_ioctl = t433_ioctl,
};
static struct miscdevice misc = {
.minor = MISC_DYNAMIC_MINOR,
.name = DEVICE_NAME,
.fops = &dev_fops,
};
static int __init dev_init(void)
{
int ret;
printk("433_dev_init\n");
//static DEFINE_SPINLOCK (cache_lock); //?
spin_lock_init(&cache_lock);
ret = gpio_request(GPIO_433, "433_pin");
if(ret < 0)
{
printk("gpio_request failed\n");
goto err_gpio_request;
}
gpio_direction_output(GPIO_433, 1);
ret = misc_register(&misc);//应该是在/dev下出那个DEVICE_NAME
printk ("size unsigned = %d\n", sizeof(unsigned));
printk (DEVICE_NAME"\tinitialized\n");
return ret;
err_gpio_request:
gpio_free(GPIO_433);
return -1;
}
static void __exit dev_exit(void)
{
printk("dev_exit\n");
}
module_init(dev_init);
module_exit(dev_exit);
MODULE_LICENSE("GPL");
MODULE_AUTHOR("xxx");
/
xx_433.h
#ifndef __XX_433_H__
#define __XX_433_H__
#define GPIO_433 (39)
#endif //__XX_433_H__
/
Makefile
#obj-$(CONFIG_XX_433) += xx_433.o
obj-m += xx_433.o
KERNELDIR:=/sdk/kernel
CROSS_COMPILE:=mips-linux-uclibc-gnu-
PWD:=$(shell pwd)
default:
$(MAKE) ARCH=mips CROSS_COMPILE=$(CROSS_COMPILE) -C $(KERNELDIR) M=$(PWD) modules
clean:
rm -rf *.o *.order .*.cmd *.ko *.mod.c *.symvers *.tmp_versions
/
insmod xx_433.ko
/
test.c
/
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/ioctl.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
int main(int argc, char **argv)
{
int on = 1;
int 433_no = 1;
int fd;
fd = open("/dev/433", 0);
if (fd < 0) {
fd = open("/dev/433", 0);
}
if (fd < 0) {
perror("open device 433");
exit(1);
}
printf("on=%x\n",on);
ioctl(fd, on, 433_no);
close(fd);
return 0;
}