📄 stepper.c
字号:
/*driver1 StepperDrive a loadable driver module stepper program for uClinux20030909(linux-2.4.x-2003-12-20) on cvtech EBD44B0. Copyright (C) Apr,2006 by Cheng-gang Shan*/#include <linux/kernel.h>#include <linux/module.h>#include <linux/interrupt.h> /* We want interrupts */#include <linux/miscdevice.h> /* for misc_register() and misc_deregister() */#include <linux/fs.h> /* for struct 'file_operations' inode,file */#include <linux/timer.h> /* for timeout interrupts */#include <linux/param.h> /* for HZ. HZ = 100 and the timer step is 1/100 */#include <linux/sched.h> /* for jiffies definition. jiffies is incremented * once for each clock tick; thus it's incremented * HZ times per secondes.*/#include <linux/mm.h> /* for verify_area#GFP_KERNEL*/#include <linux/slab.h> /* for#kmalloc(),kfree() */#include <linux/init.h> //module_exit(),module_init()#include <asm/irq.h> /* For IRQ_MACHSPEC */#include <asm/io.h> //outb()#include <asm/uaccess.h> /*get_user()*/#include <linux/types.h> //loff_t,size_t#include <asm/delay.h> //udelay()#include "stepper.h"MODULE_LICENSE("GPL");#define DEVICE_NAME "stepper"#define T 3#define num_steps 200static int i,j,k=0,p=0,t=0;static int Device_Open = 0;const int peremeter_steps=558;int delay,pulse;Stepper *motor;static int pattern[5][2][8] = { {{0x08,0x04,0x02,0x01,0x08,0x04,0x02,0x01},{0x09,0x08,0x0c,0x04,0x06,0x02,0x03,0x01}}, /*clockwise turn left curve*/ {{0x80,0x40,0x20,0x10,0x80,0x40,0x20,0x10},{0x90,0x80,0xc0,0x40,0x60,0x20,0x30,0x10}}, /*clockwise turn right curve*/ {{0x88,0x44,0x22,0x11},{0x99,0x88,0xcc,0x44,0x66,0x22,0x33,0x11}}, /*clockwise front*/ //{{0x88,0x44,0x22,0x11},{0x99,0x88,0xcc,0x44,0x66,0x22,0x33,0x11}}, /*anticlockwise fallback*/ {{0x18,0x24,0x42,0x81},{0x19,0x83,0x2c,0x64,0x46,0xc2,0x83,0x91}}, /*turn left*/ {{0x81,0x42,0x24,0x18},{0x91,0x83,0xc2,0x46,0x64,0x2c,0x38,0x19}}, /*turn right*/};static void update_stepbits(int step, unsigned int address);static void update_stepbits_half(int step, unsigned int address);static void stepper_move(Stepper *motor, int steps);static void step_left_curve(Stepper *motor, int delaytime);static void step_right_curve(Stepper *motor, int delaytime);static void busy_sleep(int loops, int mode){ int i; int a; if (mode) { for (i=0; i<loops; i++) { a=i; } } else { udelay(4000); outb(0x0,motor->io_address); udelay(loops-4000); //printk("stepper delay is %d\n",(loops-4000)); }}Stepper *stepper_create(void){ Stepper *tmp; tmp = (Stepper*)kmalloc(sizeof(Stepper),GFP_KERNEL);//内核驱动中用kmalloc分配内存 if (tmp==NULL) { return NULL; } tmp->current_phase = 0; tmp->io_address = rPDATD; tmp->curve = 0; tmp->total_steps = num_steps; tmp->sleep_mode = 0; tmp->delay =8000; tmp->current_step = 0; tmp->short_path = 0; tmp->half_stepping = 0; tmp->accelerate = 0; tmp->accelerate_from = 16000; tmp->accelerate_min = 16000; tmp->accelerate_step = 40;// tmp->accelerate_conststeps =1000; return tmp;}static int get_angle(Stepper *motor, int count){ if(motor->half_stepping) { return count*360/(2*peremeter_steps); } else { return count*360/peremeter_steps; }}static void update_stepbits(int step, unsigned int address){ switch (step) { case 0: outb(pattern[i][j][step], address);printk("0x%x\n",pattern[i][j][step]); break; case 1: outb(pattern[i][j][step], address);printk("0x%x\n",pattern[i][j][step]); break; case 2: outb(pattern[i][j][step], address);printk("0x%x\n",pattern[i][j][step]); break; case 3: outb(pattern[i][j][step], address);printk("0x%x\n",pattern[i][j][step]); break; default: outb(0x00, address); break; } }static void update_stepbits_half(int step, unsigned int address){ switch (step) { case 0: outb(pattern[i][j][step], address);printk("0x%x\n",pattern[i][j][step]); break; case 1: outb(pattern[i][j][step], address);printk("0x%x\n",pattern[i][j][step]); break; case 2: outb(pattern[i][j][step], address);printk("0x%x\n",pattern[i][j][step]); break; case 3: outb(pattern[i][j][step], address);printk("0x%x\n",pattern[i][j][step]); break; case 4: outb(pattern[i][j][step], address);printk("0x%x\n",pattern[i][j][step]); break; case 5: outb(pattern[i][j][step], address);printk("0x%x\n",pattern[i][j][step]); break; case 6: outb(pattern[i][j][step], address);printk("0x%x\n",pattern[i][j][step]); break; case 7: outb(pattern[i][j][step], address);printk("0x%x\n",pattern[i][j][step]); break; default: outb(0x00, address); break; }}static void step_forward(Stepper *motor, int delaycount){ int half_phase; if (!motor->curve) { if (motor->half_stepping) { //printf("somewhere\n"); if (motor->current_phase>3) { motor->current_phase=0; } half_phase = motor->current_phase*2; //half_phase++; if (half_phase>7) { half_phase=0; } update_stepbits_half(half_phase, motor->io_address); busy_sleep(delay/2, motor->sleep_mode); half_phase++; if (half_phase>7) { half_phase=0; } motor->current_phase++; if (motor->current_phase>3) { motor->current_phase=0; } update_stepbits_half(half_phase, motor->io_address); busy_sleep(delaycount/2, motor->sleep_mode); } else { //motor->current_phase++; if (motor->current_phase>3) { motor->current_phase=0; } update_stepbits(motor->current_phase, motor->io_address); busy_sleep(delaycount, motor->sleep_mode); motor->current_phase++; } } else { if(i==0) // turn left curve step_left_curve(motor,delaycount); if(i==1) //turn right curve step_right_curve(motor,delaycount); }}static void step_back(Stepper *motor, int delaycount){ int half_phase; if (motor->half_stepping) { //printf("somewhere\n"); half_phase = motor->current_phase*2; half_phase--; if (half_phase<0) { half_phase=7; } update_stepbits_half(half_phase, motor->io_address); busy_sleep(delay/2, motor->sleep_mode); half_phase--; if (half_phase<0) { half_phase=7; } motor->current_phase--; if (motor->current_phase<0) { motor->current_phase=3; } update_stepbits_half(half_phase, motor->io_address); busy_sleep(delaycount/2, motor->sleep_mode); } else { motor->current_phase-=1; if (motor->current_phase<0) { motor->current_phase=3; } update_stepbits(motor->current_phase, motor->io_address); busy_sleep(delaycount, motor->sleep_mode); }}static void step_left_curve(Stepper *motor, int delaytime){ int m,n; if(k > 7) k = 0; m = pattern[i][j][k]; k++; if(t!=T) { t++; if(p > 7) p = 0; //printk("%d\n",pattern[1][j][p]); n = pattern[1][j][p]; p++; pulse = m+n; printk("0x%x\n",pulse); } else { t = 0; pulse = m; printk("0x0%x\n",pulse); } outb(pulse, motor->io_address); if (motor->half_stepping) busy_sleep(delaytime/2, motor->sleep_mode); else busy_sleep(delaytime, motor->sleep_mode);}static void step_right_curve(Stepper *motor, int delaytime){ int m,n; if(k > 7) k = 0; m = pattern[i][j][k]; k++; if(t!=T) { t++; if(p > 7) p = 0; //printk("%d\n",pattern[0][j][p]); n = pattern[0][j][p]; p++; pulse = m+n; printk("0x%x\n",pulse); } else { t = 0; pulse = m; printk("0x%x0\n",pulse); } outb(pulse, motor->io_address); if (motor->half_stepping) busy_sleep(delaytime/2, motor->sleep_mode); else busy_sleep(delaytime, motor->sleep_mode);}static void stepper_gotostep(Stepper *motor, int stepnum){ if (!motor->short_path) { stepper_move(motor, stepnum-motor->current_step); } else { if ((stepnum - motor->current_step) >= 0) { if ((stepnum-motor->current_step)>motor->total_steps/2) { int move; move = motor->total_steps-(stepnum-motor->current_step); if (stepnum>motor->current_step) { move = -move; } stepper_move(motor, move); } else { stepper_move(motor, stepnum-motor->current_step); } } else { if (-(stepnum-motor->current_step) > motor->total_steps/2) { int move; move = motor->total_steps-(-(stepnum-motor->current_step)); if (stepnum>motor->current_step) { move = -move; } stepper_move(motor, move); }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -