关于作者

姓名:qq

性别:男

出生日期:1982-05-05

地区:陕西-西乡

联系电话:

QQ:40196833婚否:未婚
用户名:ququ312
笔名:真实幻影
地区: 陕西-西乡
行业:其他

日历  

快速登录

+ 用户名:
+ 密 码:

在线留言



访问统计:
文章个数:7
评论个数:5
留言条数:1




Powered by BlogDriver 2.1

真实幻影的博客

 

欢迎访问真实幻影的博客

文章

UNIX下设备驱动程序的基本结构

在UNIX系统里,对用户程序而言,设备驱动程序隐藏了设备的具体细节,对各种不同设备提供了一致的接口,一般来说是把设备映射为一个特殊的设备文件,用户程序可以象对其它文件一样对此设备文件进行操作。UNIX对硬件设备支持两个标准接口:块特别设备文件和字符特别设备文件,通过块(字符)特别设备文件存取的设备称为块(字符)设备或具有块(字符)设备接口。块设备接口仅支持面向块的I/O操作,所有I/O操作都通过在内核地址空间中的I/O缓冲区进行,它可以支持几乎任意长度和任意位置上的I/O请求,即提供随机存取的功能。

  字符设备接口支持面向字符的I/O操作,它不经过系统的快速缓存,所以它们负责管理自己的缓冲区结构。字符设备接口只支持顺序存取的功能,一般不能进行任意长度的I/O请求,而是限制I/O请求的长度必须是设备要求的基本块长的倍数。显然,本程序所驱动的串行卡只能提供顺序存取的功能,属于是字符设备,因此后面的讨论在两种设备有所区别时都只涉及字符型设备接口。设备由一个主设备号和一个次设备号标识。主设备号唯一标识了设备类型,即设备驱动程序类型,它是块设备表或字符设备表中设备表项的索引。次设备号仅由设备驱动程序解释,一般用于识别在若干可能的硬件设备中,I/O请求所涉及到的那个设备。

  设备驱动程序可以分为三个主要组成部分:

(1) 自动配置和初始化子程序,负责检测所要驱动的硬件设备是否存在和是否能正常工作。如果该设备正常,则对这个设备及其相关的、设备驱动程序需要的软件状态进行初始化。这部分驱动程序仅在初始化的时候被调用一次。
(2) 服务于I/O请求的子程序,又称为驱动程序的上半部分。调用这部分是由于系统调用的结果。这部分程序在执行的时候,系统仍认为是和进行调用的进程属于同一个进程,只是由用户态变成了核心态,具有进行此系统调用的用户程序的运行环境,因此可以在其中调用sleep()等与进程运行环境有关的函数。
(3) 中断服务子程序,又称为驱动程序的下半部分。在UNIX系统中,并不是直接从中断向量表中调用设备驱动程序的中断服务子程序,而是由UNIX系统来接收硬件中断,再由系统调用中断服务子程序。中断可以产生在任何一个进程运行的时候,因此在中断服务程序被调用的时候,不能依赖于任何进程的状态,也就不能调用任何与进程运行环境有关的函数。因为设备驱动程序一般支持同一类型的若干设备,所以一般在系统调用中断服务子程序的时候,都带有一个或多个参数,以唯一标识请求服务的设备。

  在系统内部,I/O设备的存取通过一组固定的入口点来进行,这组入口点是由每个设备的设备驱动程序提供的。一般来说,字符型设备驱动程序能够提供如下几个入口点:
(1) open入口点。打开设备准备I/O操作。对字符特别设备文件进行打开操作,都会调用设备的open入口点。open子程序必须对将要进行的I/O操作做好必要的准备工作,如清除缓冲区等。如果设备是独占的,即同一时刻只能有一个程序访问此设备,则open子程序必须设置一些标志以表示设备处于忙状态。
(2) close入口点。关闭一个设备。当最后一次使用设备终结后,调用close子程序。独占设备必须标记设备可再次使用。
(3) read入口点。从设备上读数据。对于有缓冲区的I/O操作,一般是从缓冲区里读数据。对字符特别设备文件进行读操作将调用read子程序。
(4) write入口点。往设备上写数据。对于有缓冲区的I/O操作,一般是把数据写入缓冲区里。对字符特别设备文件进行写操作将调用write子程序。
(5) ioctl入口点。执行读、写之外的操作。
(6) select入口点。检查设备,看数据是否可读或设备是否可用于写数据。select系统调用在检查与设备特别文件相关的文件描述符时使用select入口点。如果设备驱动程序没有提供上述入口点中的某一个,系统会用缺省的子程序来代替。对于不同的系统,也还有一些其它的入口点。

3.2、LINUX系统下的设备驱动程序

  具体到LINUX系统里,设备驱动程序所提供的这组入口点由一个结构来向系统进行说明,此结构定义为:
#include
struct file_operations {
int (*lseek)(struct inode *inode,struct file *filp,
off_t off,int pos);
int (*read)(struct inode *inode,struct file *filp,
char *buf, int count);
int (*write)(struct inode *inode,struct file *filp,
char *buf,int count);
int (*readdir)(struct inode *inode,struct file *filp,
struct dirent *dirent,int count);
int (*select)(struct inode *inode,struct file *filp,
int sel_type,select_table *wait);
int (*ioctl) (struct inode *inode,struct file *filp,
unsigned int cmd,unsigned int arg);
int (*mmap) (void);

int (*open) (struct inode *inode, struct file *filp);
void (*release) (struct inode *inode, struct file *filp);
int (*fsync) (struct inode *inode, struct file *filp);
};
其中,struct inode提供了关于特别设备文件/dev/driver(假设此设备名
为driver)的信息,它的定义为:
#include
struct inode {
dev_t i_dev;
unsigned long i_ino; /* Inode number */
umode_t i_mode; /* Mode of the file */
nlink_t i_nlink;
uid_t i_uid;
gid_t i_gid;
dev_t i_rdev; /* Device major and minor numbers*/
off_t i_size;
time_t i_atime;
time_t i_mtime;
time_t i_ctime;
unsigned long i_blksize;
unsigned long i_blocks;
struct inode_operations * i_op;
struct super_block * i_sb;
struct wait_queue * i_wait;
struct file_lock * i_flock;
struct vm_area_struct * i_mmap;
struct inode * i_next, * i_prev;
struct inode * i_hash_next, * i_hash_prev;
struct inode * i_bound_to, * i_bound_by;
unsigned short i_count;
unsigned short i_flags; /* Mount flags (see fs.h) */
unsigned char i_lock;
unsigned char i_dirt;
unsigned char i_pipe;
unsigned char i_mount;
unsigned char i_seek;
unsigned char i_update;
union {
struct pipe_inode_info pipe_i;
struct minix_inode_info minix_i;
struct ext_inode_info ext_i;
struct msdos_inode_info msdos_i;
struct iso_inode_info isofs_i;
struct nfs_inode_info nfs_i;
} u;
};

struct file主要用于与文件系统对应的设备驱动程序使用。当然,其它设 备驱动程序也可以使用它。它提供关于被打开的文件的信息,定义为:
#include
struct file {
mode_t f_mode;
dev_t f_rdev; /* needed for /dev/tty */
off_t f_pos; /* Curr. posn in file */
unsigned short f_flags; /* The flags arg passed to open */
unsigned short f_count; /* Number of opens on this file */
unsigned short f_reada;
struct inode *f_inode; /* pointer to the inode struct */
struct file_operations *f_op;/* pointer to the fops struct*/
};

  在结构file_operations里,指出了设备驱动程序所提供的入口点位置,分 别是:
(1) lseek,移动文件指针的位置,显然只能用于可以随机存取的设备。
(2) read,进行读操作,参数buf为存放读取结果的缓冲区,count为所要 读取的数据长度。返回值为负表示读取操作发生错误,否则返回实际读取 的字节数。对于字符型,要求读取的字节数和返回的实际读取字节数都必
须是inode->i_blksize的的倍数。
(3) write,进行写操作,与read类似。
(4) readdir,取得下一个目录入口点,只有与文件系统相关的设备驱动程序 才使用。
(5) selec,进行选择操作,如果驱动程序没有提供select入口,select操 作将会认为设备已经准备好进行任何的I/O操作。
(6) ioctl,进行读、写以外的其它操作,参数cmd为自定义的的命令。
(7) mmap,用于把设备的内容映射到地址空间,一般只有块设备驱动程序使 用。
(8) open,打开设备准备进行I/O操作。返回0表示打开成功,返回负数表 示失败。如果驱动程序没有提供open入口,则只要/dev/driver文件存 在就认为打开成功。
(9) release,即close操作。 设备驱动程序所提供的入口点,在设备驱动程序初始化的时候向系统进行登 记,以便系统在适当的时候调用。LINUX系统里,通过调用register_chrdev 向系统注册字符型设备驱动程序。register_chrdev定义为:
#include
#include
int register_chrdev(unsigned int major, const char *name,
struct file_operations *fops);
   其中,major是为设备驱动程序向系统申请的主设备号,如果为0则系统为此 驱动程序动态地分配一个主设备号。name是设备名。fops就是前面所说的对各个 调用的入口点的说明。此函数返回0表示成功。返回-EINVAL表示申请的主设备号 非法,一般来说是主设备号大于系统所允许的最大设备号。返回-EBUSY表示所申 请的主设备号正在被其它设备驱动程序使用。如果是动态分配主设备号成功,此 函数将返回所分配的主设备号。如果register_chrdev操作成功,设备名就会出 现在/proc/devices文件里。
   初始化部分一般还负责给设备驱动程序申请系统资源,包括内存、中断、时 钟、I/O端口等,这些资源也可以在open子程序或别的地方申请。在这些资源不 用的时候,应该释放它们,以利于资源的共享。 在UNIX系统里,对中断的处理是属于系统核心的部分,因此如果设备与系
统之间以中断方式进行数据交换的话,就必须把该设备的驱动程序作为系统核心 的一部分。设备驱动程序通过调用request_irq函数来申请中断,通过free_irq 来释放中断。它们的定义为:
#include
int request_irq(unsigned int irq,
void (*handler)(int irq,void dev_id,struct pt_regs *regs),
unsigned long flags,
const char *device,
void *dev_id);
void free_irq(unsigned int irq, void *dev_id);

参数说明:

  参数irq表示所要申请的硬件中断号。handler为向系统登记的中断处理子 程序,中断产生时由系统来调用,调用时所带参数irq为中断号,dev_id为申 请时告诉系统的设备标识,regs为中断发生时寄存器内容。device为设备名, 将会出现在/proc/interrupts文件里。flag是申请时的选项,它决定中断处理 程序的一些特性,其中最重要的是中断处理程序是快速处理程序(flag里设置
了SA_INTERRUPT)还是慢速处理程序(不设置SA_INTERRUPT),快速处理程序 运行时,所有中断都被屏蔽,而慢速处理程序运行时,除了正在处理的中断外, 其它中断都没有被屏蔽。在LINUX系统中,中断可以被不同的中断处理程序共享, 这要求每一个共享此中断的处理程序在申请中断时在flags里设置SA_SHIRQ, 这些处理程序之间以dev_id来区分。如果中断由某个处理程序独占,则dev_id 可以为NULL。request_irq返回0表示成功,返回-INVAL表示irq>15或 handler==NULL,返回-EBUSY表示中断已经被占用且不能共享。 作为系统核心的一部分,设备驱动程序在申请和释放内存时不是调用malloc 和free,而代之以调用kmalloc和kfree,它们被定义为:
#include
void * kmalloc(unsigned int len, int priority);
void kfree(void * obj);
   参数len为希望申请的字节数,obj为要释放的内存指针。priority为分配内存操 作的优先级,即在没有足够空闲内存时如何操作,一般用GFP_KERNEL。   与中断和内存不同,使用一个没有申请的I/O端口不会使CPU产生异常,也 就不会导致诸如“segmentation fault"一类的错误发生。任何进程都可以访问 任何一个I/O端口。此时系统无法保证对I/O端口的操作不会发生冲突,甚至会 因此而使系统崩溃。因此,在使用I/O端口前,也应该检查此I/O端口是否已有 别的程序在使用,若没有,再把此端口标记为正在使用,在使用完以后释放它。
这样需要用到如下几个函数:
int check_region(unsigned int from, unsigned int extent);
void request_region(unsigned int from, unsigned int extent,
const char *name);
void release_region(unsigned int from, unsigned int extent);
   调用这些函数时的参数为:from表示所申请的I/O端口的起始地址; extent为所要申请的从from开始的端口数;name为设备名,将会出现在
/proc/ioports文件里。check_region返回0表示I/O端口空闲,否则为正在 被使用。
   在申请了I/O端口之后,就可以如下几个函数来访问I/O端口:
#include
inline unsigned int inb(unsigned short port);
inline unsigned int inb_p(unsigned short port);
inline void outb(char value, unsigned short port);
inline void outb_p(char value, unsigned short port);
   其中inb_p和outb_p插入了一定的延时以适应某些慢的I/O端口。 在设备驱动程序里,一般都需要用到计时机制。在LINUX系统中,时钟是由 系统接管,设备驱动程序可以向系统申请时钟。与时钟有关的系统调用有:
#include
#include
void add_timer(struct timer_list * timer);
int del_timer(struct timer_list * timer);
inline void init_timer(struct timer_list * timer);
struct timer_list的定义为:
struct timer_list {
struct timer_list *next;
struct timer_list *prev;
unsigned long expires;
unsigned long data;
void (*function)(unsigned long d);
};
   其中expires是要执行function的时间。系统核心有一个全局变量JIFFIES 表示当前时间,一般在调用add_timerjiffies=JIFFIES+num,表示在num个 系统最小时间间隔后执行function。系统最小时间间隔与所用的硬件平台有关, 在核心里定义了常数HZ表示一秒内最小时间间隔的数目,则num*HZ表示num 秒。系统计时到预定时间就调用function,并把此子程序从定时队列里删除, 因此如果想要每隔一定时间间隔执行一次的话,就必须在function里再一次调 用add_timer。function的参数d即为timer里面的data项。
   在设备驱动程序里,还可能会用到如下的一些系统函数:
#include
#define cli() __asm__ __volatile__ ("cli"::)
#define sti() __asm__ __volatile__ ("sti"::)
这两个函数负责打开和关闭中断允许。
#include
void memcpy_fromfs(void * to,const void * from,unsigned long n);
void memcpy_tofs(void * to,const void * from,unsigned long n);
   在用户程序调用read 、write时,因为进程的运行状态由用户态变为核心 态,地址空间也变为核心地址空间。而read、write中参数buf是指向用户程 序的私有地址空间的,所以不能直接访问,必须通过上述两个系统函数来访问用 户程序的私有地址空间。memcpy_fromfs由用户程序地址空间往核心地址空间 复制,memcpy_tofs则反之。参数to为复制的目的指针,from为源指针,n 为要复制的字节数。
   在设备驱动程序里,可以调用printk来打印一些调试信息,用法与printf 类似。printk打印的信息不仅出现在屏幕上,同时还记录在文件syslog里。

3.3、LINUX系统下的具体实现
   在LINUX里,除了直接修改系统核心的源代码,把设备驱动程序加进核心里 以外,还可以把设备驱动程序作为可加载的模块,由系统管理员动态地加载它, 使之成为核心地一部分。也可以由系统管理员把已加载地模块动态地卸载下来。 LINUX中,模块可以用C语言编写,用gcc编译成目标文件(不进行链接,作 为*.o文件存在),为此需要在gcc命令行里加上-c的参数。在编译时,还应该在 gcc的命令行里加上这样的参数:-D__KERNEL__ -DMODULE。由于在不链接时, gcc只允许一个输入文件,因此一个模块的所有部分都必须在一个文件里实现。
编译好的模块*.o放在/lib/modules/xxxx/misc下(xxxx表示核心版本,如 在核心版本为2.0.30时应该为/lib/modules/2.0.30/misc),然后用depmod -a 使此模块成为可加载模块。模块用insmod命令加载,用rmmod命令来卸载,并可 以用lsmod命令来查看所有已加载的模块的状态。
   编写模块程序的时候,必须提供两个函数,一个是int init_module(void), 供insmod在加载此模块的时候自动调用,负责进行设备驱动程序的初始化工作。 init_module返回0以表示初始化成功,返回负数表示失败。另一个函数是void cleanup_module (void),在模块被卸载时调用,负责进行设备驱动程序的清除 工作。
   在成功的向系统注册了设备驱动程序后(调用register_chrdev成功后), 就可以用mknod命令来把设备映射为一个特别文件,其它程序使用这个设备的时 候,只要对此特别文件进行操作就行了。

- 作者: 真实幻影 2005年08月30日, 星期二 19:40  回复(0) |  引用(0) 加入博采

标准时间

- 作者: 真实幻影 2005年06月25日, 星期六 14:17  回复(0) |  引用(0) 加入博采

qq显示在线状态
<A href="http://wpa.qq.com/msgrd?V=1&amp;Uin=40196833&amp;Exe=QQ&amp;Menu=yes" target=blank><IMG alt=点击与我联系 src="http://wpa.qq.com/pa?p=1:40196833:7" border=0> </A>

- 作者: ququ312 2005年06月8日, 星期三 11:26  回复(0) |  引用(0) 加入博采

linux qq

今天,试了一下,在TURBO LINUX下使用QQ,原来很简单呀!

不过很是佩服清华这位开发Luma qq 的人,真有一套,将JAVA 的跨平台能力发挥了出来,真不错!

不过发现LINUX 这些打着开源软件的东西,还是要注册,而且TURBO LINUX 汉化的好厉害呀,原来

用SCO UNIX 的我好多命令都不能用了!

- 作者: ququ312 2005年06月4日, 星期六 16:21  回复(0) |  引用(0) 加入博采

sco 多用户卡安装
作为一名网络管理员,会面对各种各样的故障,而故障现象可能千奇百怪,原因也多种多样。要快速、准确的定位和处理故障,需要网络管理员有比较扎实的网络理论基础和丰富的实践经验。同时,还要求网络管理员掌握一些操作系统的网络设置等方面的知识。在日常的网络故障中,物理层、链路层和网络层这下三层的故障占了70%以上,应用层等上三层约占了30%,其中尤以物理层的问题居多,而应用层一旦出了问题,排查就比较困难。在这里,笔者谈谈去年曾经处理过的一例并不常见的涉及系统层面的通讯故障,但具有比较典型的意义。
系统介绍
故障系统是我行与移动公司的联网实时代收费系统。移动公司前置机用的是SCO Unix操作系统平台,Informix数据库,通过一个多用户卡串行连接各个代收费银行和单位。由于历史的原因,在移动公司代收费系统中,不同的代收费单位有不同的接口服务进程,系统配置也不尽相同;我行的前置机用Windows NT系统平台,通过串口以DTU到DTU方式直连到移动公司,双方以19200bps速率连接,连接如下图1:
(IMG:http://www.netadmin.com.cn/experience/20040701/beryl20040701164619.jpg)(screen.width*0.8-400)) this.width=(screen.width*0.8-400)'>
故障现象
我行和移动公司的联网代收费系统已正常运行了一个多月,国庆节休假回来第一天早上,发现交易异常:我行发送到移动公司收费前置机的数据包,如泥牛入海,全部收不到返回包。
诊断处理过程
面对这种情况,首先想到的是对方可能没有启动业务系统,于是打电话问对方,回复说收到乱码,所以没有数据包返回,同时反映说其他行到移动公司的交易也做不了,但其他代收费单位没有问题,业务交易正常。笔者马上想到通讯问题,致电电信公司的数据局检查和测试线路,看看是否出现通讯线路故障。经检查,数据局反映工行的问题是局端的交换端口出现了故障,更换设备后,下午交易恢复正常。但反馈说我行的线路正常,误码率也在正常范围之内。于是问数据局是否更改过速率,回答说没有。
后来想想,会不会是移动公司的多用户串口或我们服务器的串口坏了呢?于是双方协调各自调换了端口,故障依旧。而后笔者问对方可有改动过配置文件或程序,回复说没有。
这就奇怪了,因为通讯和应用系统接口一经确定,正常情况下是不会变更的,之前双方系统已经正常运行了一个多月,双方程序亦无改动过。因为是走串口,而不是走TCP/IP方式,所以无法用ping等网络工具进行诊断,这就给故障的诊断带来了一定困难。前面的诊断未能彻底排除中间环节(如:多用户卡的串口单点或多点故障)是否存在问题,那到底是中间环节出问题了呢,还是因为不小心变动了系统配置而导致故障的出现?
为了确定故障点,笔者决定到移动公司去一趟,跳过多用户卡,直连其串口进行测试。到移动公司后,打开手提电脑,接好直连线,启用超级终端后,看不到SCO Unix的login登陆画面。不可能!因为移动公司证实该串口是好的,SCO Unix的串口也已经激活启用,怎么回事?真是一波未平一波又起!难道是转接头接线不对吗?我检查了一下线序,没问题啊,再看看超级终端的设置:
波特率:9600bps
数据位:8位
校验: 无奇偶校验
停止位:1位
流控: 硬件
都是典型的设置,为什么没有终端画面出现呢?后来想到硬件流控是需要有专门的信号线来控制(我的转接线是临时做的,只用了收、发和信号地3根线缆,没有用到其他的信号线),故调整了超级终端的流控(把硬件流控改为软件流控Xon/Xoff),login的终端画面出现,但还是做不了业务交易,故障依旧,这样彻底排除了中间环节的链路故障。既然双方都没有改动过程序,那肯定是双方系统或应用设置的速率不匹配造成的。
到底是哪里的速率配置出问题呢?我们看了彼此的应用通讯设置,是一样的,都是19200bps,奇怪,到底怎么回事?这时,我突然想起会不会是串口的速率设置问题,但移动公司的工程师很确切地说:并没有更改过参数啊!仔细思量,其它可能的情况都排除了,就剩下这里了,于是决定还是检查一下,我们查看了SCO Unix的/etc/inittab文件,显示如下:
......
Se1a:234: respawn:/etc/getty tty1a m (以下4行为标准串口设置)
Se1A:234:off:/etc/getty -t60 tty1A 3
Se2a:234:respawn:/etc/getty tty2a m
Se2A:234:off:/etc/getty -t60 tty2A 3
......
ma11:23: respawn:/etc/getty ttya11 m (以下部分为多用户串口设置)
mA11:23: off:/etc/getty ttyA11 o
ma12:23: respawn:/etc/getty ttya12 m
mA12:23: off:/etc/getty ttyA12 o
......
发现用于我行的端口速率设置为m (9600bps)(见划线部分),问题就出在这里了。
把定义我行通讯的划线部分由速率m (9600bps) 改为n (19200bps),即修改为:ma12:23: respawn:/etc/getty ttya12 n
同时修改/etc/conf/cf.d/init.base及相应的多用户卡配置文件/etc/conf/init.d/moxa的相应内容,(这两个文件在Unix重新链接核心时会生成新的inittab文件覆盖原来的/etc/inittab文件,如不更改,核心重链时会导致修改后的/etc/inittab文件配置失效)。
重新启动接口服务进程,故障排除,业务交易恢复正常。
故障原因
在银行与移动公司之间的通讯链路虽然采用了64K的DDN(数字数据网),但因为DDN是一种采用数字交叉连接技术和时分复用技术的全透明传输网,可以面向各类数据用户,所以在这段通讯链路上没问题。然而由于在Unix系统中串口不具备速率自适应功能,导致在系统端口速率不匹配,解码错误,出现乱码。故障产生的原因可能有两个:
1.可能是因为对方的失误,在检查系统时,犯了经验主义错误,以为我行的速率也应该是9600bps,不小心更改了配置参数导致(因为除我行外,其他银行和代收费单位均采用系统默认的9600bps配置速率)。
2.可能是因为在上一次Unix核心链接后,才上了该收费系统并修改了/etc/inittab文件,但未同时修改Unix核心链接源文件/etc/conf/cf.d/init.base及相应的多用户卡配置文件/etc/conf/init.d/moxa的相应内容,使得这几个配置文件的内容并不完全吻合,而后因为机器硬件或软件的变更(如增加、删除等)重新进行了Unix的核心链接,使得核心重新链接后,新的目标配置文件/etc/inittab的配置参数变了,导致了故障的出现。
排除心得
从这个问题出发,我们可以看出,作为一位网络管理员,不仅需要掌握网络方面的知识,也必须具备各种操作系统方面的一些相关知识,特别是系统上与通讯配置相关的知识。了解、掌握与之相关的配置文件和参数,对于我们处理故障,将会大有裨益,可大大缩短故障处理时间。同时,在系统规划和设计上,应尽量采用一些系统缺省的或常用的、典型的参数,这可避免许多类似问题的出现,减少系统故障出现的几率和维护成本。另外,在故障排除时,不可完全依赖经验和记忆,因为有时经验和记忆并不完全可靠(例如这次故障,对方凭记忆说没有更改过配置参数,而实际上却是更改了,不管是有意还是无意),这就给故障的排除设置了一个错觉和障碍,反而影响了故障的排除效率。
以上是笔者的一点心得和体会,借此抛砖引玉,希望能够和大家一起交流,给大家带来一点启发与思考。
[编辑提示:]
1. 在SCO Unix中,/dev/tty1a与/dev/tty1A实际上是同一个串行端口(/dev/tty2a与/dev/tty2A也是如此)。对于每一种设备,操作系统使用不同的设备驱动子程序。/dev/ttyA* 或 /dev/tty*A是用于modem拨号的设备,而/dev/ttya*或/dev/tty*a是用于串口连接的,两者不能同时使用,否则将会看到警告信息:
Cannot open:device busy.
2.在SCO Unix中,速率m代表9600bps,n 代表19200bps,o代表38400bps,该定义在/etc/gettydefs中有定义。
-例:MOXAC104/168P多用户卡SCO UNIX下的安装
1、将卡右上脚的跳线JP1插上。
2、打开电源,将DOS的驱动盘插入软驱。
3、进入DOS,打入A:IO-IRQ,回车。
4、直接回车。
5、Enter the "configuration Access port" in HEX 后打入A700。
6、出现表格
7、按F3键,选第一项后回车。
8、按F10键退出并保存,按ESC键退出。
9、关机后将JP1拔掉。
10、进入UNIX按装。
11、#MKDEV SERIAL (进入UNIX后)。
12、进入后按TAB键选Add项,回车。
13、移动光标进行选项:
Description Ports IRQ:4
Arnet 8 I/Q:280
14、回车。
15、按ESC键,连接核心打Y。连接核心后#enable /dev/tty1[A-H]激活端口,重新起动计算机。

- 作者: ququ312 2005年06月2日, 星期四 22:56  回复(0) |  引用(0) 加入博采

gmail邮箱终于申请到了!

应该感谢一下cfan的同志们,isnoop.net间接获取了GAMIL邮箱!zzzzzzzzzzz

- 作者: ququ312 2005年06月1日, 星期三 10:13  回复(5) |  引用(0) 加入博采

初次登陆

初登博客,不知博客为何物????????????看了半天,好象意思是网络日志吧!

- 作者: ququ312 2005年05月31日, 星期二 11:09  回复(0) |  引用(0) 加入博采