⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 printf.c,v

📁 一个小型的操作系统,采用gcc进行开发,几千行的代码,方便初学者学习
💻 C,V
字号:
head	1.3;access;symbols;locks	root:1.3; strict;comment	@ * @;1.3date	2004.06.01.02.59.13;	author root;	state Exp;branches;next	1.2;1.2date	2004.05.24.13.29.03;	author root;	state Exp;branches;next	1.1;1.1date	2004.05.24.12.34.29;	author root;	state Exp;branches;next	;desc@@1.3log@add fprintf()@text@/*  Snixos Project version 1.0, 2003.6  (C) Copyright 2003-2004 Snallie Jockeyson <Snallie@@tom.com>  All Rights Reserved.  Distributed under the terms of the GNU General Public License.  printf.c: implementation of c function printf() in SNIXOS project  Author  : snallie@@tom.com  Time    : 2003.6  understood printf escape sequence:  %c = char     %d = signed int    %x = unpaded hex  %s = string   %0x = padded hex   %o = octal   %b = binary*//* 	$Id: printf.c,v 1.2 2004/05/24 13:29:03 root Exp $	 */#ifndef lintstatic char vcid[] = "$Id: printf.c,v 1.2 2004/05/24 13:29:03 root Exp $";#endif				/* lint */#include "stdarg.h"#include "stdio.h"#include "ctype.h"#include "io.h"#include "mem.h"#include "fatfs.h"#define RESERVEDLINES 1		// head line reserved as status bar, 0 means the whole screen				//  will be scrolled #define XUPPER 1#define XLOWER 0// Video Card I/O ports#define TEXT_INDEX      0x03D4#define TEXT_DATA       0x03D5// Video Card Index Registers#define TEXT_CURSOR_LO  0x0F#define TEXT_CURSOR_HI  0x0Estatic void printChar(char **str, int *len, char c);static void printStr(char **str, int *len, char *pstr);static void printInt(char **str, int *len, int num, int width);static void printHex(char **str, int *len, unsigned int hex,		     int padded, int style);static void vaPrintf(char **str, int *len, char *fmt, va_list pvar);static unsigned char getChar(int x, int y);static unsigned char getAttrib(int x, int y);static void scrollup(void);static void writeChar(char c);static void TXTWriteChar(char c);static int intLen(int i, int radix);static unsigned char *vidmem;	/* VGA video buffer for 80*25 color text mode */static int vidx;		/* current cursor X position on screen */static int vidy;		/* current cursor Y position on screen */static unsigned char curAttrib;	/* current screent text attribute */extern int videoMode;/*  * console output functions */void print_char(char c){    int i = -1;    printChar(NULL, &i, c);}void print_str(char *str){    int i = -1;    printStr(NULL, &i, str);}void print_int(int num){    int i = -1;    printInt(NULL, &i, num, 0);}void print_hex(unsigned int hex, int padded){    int i = -1;    printHex(NULL, &i, hex, padded, XLOWER);}void printf(char *fmt, ...){    int i = -1;    va_list pvar;    va_start(pvar, fmt);    vaPrintf(NULL, &i, fmt, pvar);    va_end(pvar);}void sprintf(char *str, char *fmt, ...){    int i = -1;    va_list pvar;    va_start(pvar, fmt);    vaPrintf(&str, &i, fmt, pvar);    va_end(pvar);}void snprintf(char *str, int len, char *fmt, ...){    va_list pvar;    va_start(pvar, fmt);    vaPrintf(&str, &len, fmt, pvar);    va_end(pvar);}int fprintf(FILE * fp, char *fmt, ...){    char nstr[100];    int i = -1;    char *str = nstr;    va_list pvar;    va_start(pvar, fmt);    vaPrintf(&str, &i, fmt, pvar);    va_end(pvar);    i = 0;    while (*(str + i)) {	Mfputc(*(str + i), fp);	printf("%c", *(str + i));	i++;    }    return i;}/*  * base functions for printf implementation */static void printChar(char **str, int *len, char c){    if (str) {	if (*len != 0) {	    *(*str)++ = c;	    (*len)--;	}    } else {	writeChar(c);    }}static void printStr(char **str, int *len, char *pstr){    while (*pstr) {	printChar(str, len, *pstr);	pstr++;    }}/*printInt()print the num in decimal mode*/static void printInt(char **str, int *len, int num, int width){    char nstr[12];    int i = 10, j = 0;    if (num < 0) {	printChar(str, len, '-');	printInt(str, len, -1 * num, width - 1);	return;    }    nstr[11] = '\0';    while (i > 0) {	nstr[i % 11] = '0' + (num % 10);	num /= 10;	i--;	if ((j >= width - 1) && (num <= 0))	    break;	else	    j++;    }    printStr(str, len, nstr + i + 1);}/*printHex()printf the hex in hexadecimal mode */static void printHex(char **str, int *len, unsigned int hex,		     int pad, int style){    char nstr[14];    int i = 12, j;    nstr[13] = '\0';    pad--;    for (j = 0; j < 8; j++) {	if ((hex % 16) < 10)	    nstr[i] = '0' + (hex % 16);	else	    nstr[i] = ((style == XLOWER) ? 'a' : 'A') + ((hex % 16) - 10);	hex /= 16;	i--;	if ((j >= pad) && (hex <= 0))	    break;    }    printStr(str, len, nstr + i + 1);}/*void printOct(char **str, int *len, unsigned int num)print the integer num in octal mode */static void printOct(char **str, int *len, unsigned int num){    int octLen = intLen(num, 8), i;    char *octbuf = (char *) malloc((octLen + 1) * sizeof(char));    if (octbuf == NULL) {	printf("malloc failed in printOct\n");	return;    }    i = octLen - 1;    octbuf[octLen] = '\0';    while (num) {	octbuf[i % octLen] = num % 8 + '0';	num /= 8;	i--;    }    printStr(str, len, octbuf + i + 1);    free(octbuf);}/*void printBin(char **str, int *len, unsigned int num)print the integer num in binary mode */static void printBin(char **str, int *len, unsigned int num){    int len2;    int binLen = intLen(num, 2), i;    char *binbuf =	(char *) malloc(((binLen - 1) / 8 + 1) * 8 * sizeof(char) +			sizeof(char));    if (binbuf == NULL) {	printf("malloc failed in printBin\n");	return;    }    len2 = ((binLen - 1) / 8 + 1) * 8 * sizeof(char) + sizeof(char);    i = ((binLen - 1) / 8 + 1) * 8 * sizeof(char) - 1;    binbuf[((binLen - 1) / 8 + 1) * 8 * sizeof(char)] = '\0';    while (i >= 0) {	binbuf[i % len2] = num % 2 + '0';	num /= 2;	i--;    }    printStr(str, len, binbuf + i + 1);    free(binbuf);}static void vaPrintf(char **str, int *len, char *fmt, va_list pvar){    while (*fmt) {	if (*fmt == '%') {	    fmt++;	    if (!*fmt) {		if (str) {	/*  add end of line to array tp for sprintf(tp,char * ,...) */		    printChar(str, len, '\0');		}		return;	    }	    switch (*fmt) {	    case 's':		/* %s */		printStr(str, len, va_arg(pvar, char *));		break;	    case 'c':		/* %c */		printChar(str, len, va_arg(pvar, char));		break;	    case 'd':		/* %d */		printInt(str, len, va_arg(pvar, int), 0);		break;	    case 'x':	    case 'X':		/* %x or %X */		printHex(str, len, va_arg(pvar, unsigned int), 0,			 (*fmt == 'x') ? XLOWER : XUPPER);		break;	    case 'o':		/* %o */		printOct(str, len, va_arg(pvar, unsigned int));		break;	    case 'b':		/* %b , binary output for number */		printBin(str, len, va_arg(pvar, unsigned int));		break;	    case '0':		/* %0x %0X %0d */		fmt++;		switch (*fmt) {		case 'x':		case 'X':		    printHex(str, len,			     va_arg(pvar, unsigned int), 8,			     (*fmt == 'x') ? XLOWER : XUPPER);		    goto ret1;		case 'd':		    printInt(str, len, va_arg(pvar, int), 10);		    goto ret1;		}		if (isdigit(*fmt)) {		    int width = 0;		    while (isdigit(*fmt)) {			width = (width * 10 + (*fmt) - '0');			fmt++;		    }		    if (*fmt == 'x' || *fmt == 'X') {			printHex(str, len,				 va_arg(pvar, unsigned int), width,				 *fmt == 'x' ? XLOWER : XUPPER);		    } else if (*fmt == 'd') {			printInt(str, len, va_arg(pvar, int), width);		    }		}	      ret1:		break;	    case '1':	    case '2':	    case '3':	    case '4':	    case '5':	    case '6':	    case '7':	    case '8':	    case '9':		/* %12x %12X %12d %12s %12c */		if (isdigit(*fmt)) {		    int width;		    for (width = 0; isdigit(*fmt); fmt++) {			width = (width * 10 + (*fmt) - '0');		    }		    if (*fmt == 'x' || *fmt == 'X') {			printHex(str, len,				 va_arg(pvar, unsigned int), width,				 *fmt == 'x' ? XLOWER : XUPPER);		    } else if (*fmt == 'd') {			int num = va_arg(pvar, int);			int length = intLen(num, 10);			while (width > length) {			    printChar(str, len, ' ');			    width--;			}			printInt(str, len, num, length);		    } else if (*fmt == 's') {			char *strs = va_arg(pvar, char *);			int strSize = strlen(strs);			while (width - strSize > 0) {			    printChar(str, len, ' ');			    strSize++;			}			printStr(str, len, strs);		    } else if (*fmt == 'c') {			width -= 1;			while (width > 0) {			    printChar(str, len, ' ');			    width--;			}			printChar(str, len, va_arg(pvar, char));		    }		}		break;	    case '-':		/* %-12s  %-12d  %-12c , left aligned */		fmt++;		if (isdigit(*fmt)) {		    int width = 0;		    while (isdigit(*fmt)) {			width = (width * 10 + (*fmt) - '0');			fmt++;		    }		    if (*fmt == 's') {			char *strs = va_arg(pvar, char *);			int strSize = strlen(strs);			printStr(str, len, strs);			while (width - strSize > 0) {			    printChar(str, len, ' ');			    strSize++;			}		    } else if (*fmt == 'd') {			int num = va_arg(pvar, int);			int length = intLen(num, 10);			printInt(str, len, num, length);			while (width - length > 0) {			    printChar(str, len, ' ');			    length++;			}		    } else if (*fmt == 'c') {			printChar(str, len, va_arg(pvar, char));			width -= 1;			while (width > 0) {			    printChar(str, len, ' ');			    width--;			}		    }		}		break;	    case '%':		/* %% */		printChar(str, len, '%');		fmt++;		break;	    default:		break;	    }	} else {	    printChar(str, len, *fmt);	}	fmt++;    }				/* while(*fmt) */    if (str) {			/* add end of line to array tp for sprintf(tp,char *fmt, ...) */	printChar(str, len, '\0');    }}/*int intLen(int i, int radix)     return the count of i's digit which is beneath     the most significant digit in the desired radix. */static int intLen(int i, int radix){    int len = 0;    if (i < 0) {	return intLen(-i, radix);    }    do {	i /= radix;	len++;    } while (i);    return len;}/* VGA screen manipulation */void screen_init(void){    int i, j;    vidmem = (unsigned char *) 0xb8000;    set_attrib(ATTRIB_WHITE | ATTRIB_BLACK_BG);    for (i = 0; i < 80; i++) {	for (j = 0; j < 25; j++) {	    screen_putchar(i, j, ' ', curAttrib);	}    }    //line 1 reserved as status bar    screen_gotoxy(0, 0 + RESERVEDLINES);}void screen_gotoxy(int x, int y){    short pos = y * 80 + x;    vidx = x;    vidy = y;    outb(TEXT_CURSOR_LO, TEXT_INDEX);	// access lo cursor data reg    outb((char) pos, TEXT_DATA);    outb(TEXT_CURSOR_HI, TEXT_INDEX);	// access hi cursor data reg    outb((unsigned char) (pos >> 8), TEXT_DATA);}void screen_putchar(int x, int y, unsigned char c, unsigned char attrib){    vidmem[((x) + (y) * 80) * 2] = c;    vidmem[(((x) + (y) * 80) * 2) + 1] = attrib;}static unsigned char getChar(int x, int y){    return vidmem[((x) + (y) * 80) * 2];}static unsigned char getAttrib(int x, int y){    return vidmem[(((x) + (y) * 80) * 2) + 1];}static void scrollup(void){    unsigned int org = (unsigned int) vidmem + (RESERVEDLINES + 1) * 160;    unsigned int dst = (unsigned int) vidmem + RESERVEDLINES * 160;    unsigned int cnt = 2000 - 80 * (RESERVEDLINES + 1);    unsigned int cnt2 = 80;	/* characters to be displaed at the bottom line on screen */    unsigned int dst2 = (unsigned int) vidmem + 24 * 80 * 2;	/* bottom line address in vidram */    asm("cld\n\t" "rep\n\t" "movsl\n\t"::"c"(cnt), "D"(dst), "S"(org));    asm("cld\n\t"	"rep\n\t" "stosw\n\t"::"a"(0x0720), "c"(cnt2), "D"(dst2),	"S"(org));}static void writeChar(char c){    switch (videoMode) {    case VIDTEXT_80X25:	TXTWriteChar(c);	break;    case VIDGRAPH_640X480:	VGAWriteChar(c);	break;    }}static void TXTWriteChar(char c){    if (c == '\n') {		// CR LF	screen_gotoxy(0, ++vidy);	// screen_gotoxy(ycord,xcord)    } else if (c == '\t') {	// horizontal Tab	screen_gotoxy(vidx += 4, vidy);    } else if (c == '\b') {	// backspace	screen_gotoxy(vidx -= 1, vidy);	writeChar(' ');	screen_gotoxy(vidx -= 1, vidy);	return;    } else {	screen_putchar(vidx, vidy, (unsigned char) c, curAttrib);	screen_gotoxy(++vidx, vidy);    }    // off right edge    if (vidx > 79) {	screen_gotoxy(0, ++vidy);    }    // off bottom    if (vidy > 24) {	scrollup();	screen_gotoxy(vidx, 24);    }}void set_attrib(unsigned char attrib){    curAttrib = attrib;}@1.2log@add comments to some auxilary function@text@d18 1a18 1/* 	$Id$	 */d21 2a22 2static char vcid[] = "$Id$";#endif /* lint */d29 1d46 1a46 1			   int padded, int style);d52 1d59 1a59 1d114 21d191 1a191 1			   int pad, int style)d271 1a271 1		if (str){	/*  add end of line to array tp for sprintf(tp,char * ,...)*/d292 1a292 1			       (*fmt == 'x') ? XLOWER : XUPPER);d309 2a310 2				   va_arg(pvar, unsigned int), 8,				   (*fmt == 'x') ? XLOWER : XUPPER);d326 2a327 2				       va_arg(pvar, unsigned int), width,				       *fmt == 'x' ? XLOWER : XUPPER);d352 2a353 2				       va_arg(pvar, unsigned int), width,				       *fmt == 'x' ? XLOWER : XUPPER);d431 1a431 1    } /* while(*fmt) */d433 1a433 1    if (str){			/* add end of line to array tp for sprintf(tp,char *fmt, ...) */d446 1a446 1    if (i < 0){d515 15d553 1a559 7@1.1log@Initial revision@text@d12 1a12 1  understood printf escape chars:d18 6d34 6a52 8// Video Card I/O ports#define TEXT_INDEX      0x03D4#define TEXT_DATA       0x03D5// Video Card Index Registers#define TEXT_CURSOR_LO  0x0F#define TEXT_CURSOR_HI  0x0Ed113 1a113 1 * core functionsd135 4a159 1d163 4a174 1a184 1a185 1d188 4d212 4a217 1a241 1a306 1a307 2a325 46		    /*		       switch (*fmt) {		       case 'x':		       case 'X':		       printHex(str, len,		       va_arg(pvar, unsigned int), width,		       *fmt == 'x' ? XLOWER : XUPPER);		       break;		       case 'd':		       {		       int num = va_arg(pvar, int);		       int length = intLen(num, 10);		       while (width > length) {		       printf("%c", ' ');		       width--;		       }		       printf("%d", num);		       }		       break;		       case 's':		       {		       char *strs = va_arg(pvar, char *);		       int strSize = strlen(strs);		       while (width > strSize) {		       printf("%c", ' ');		       strSize++;		       }		       printf("%s", strs);		       }		       break;		       case 'c':		       {		       width -= 1;		       while (width > 0) {		       printf("%c", ' ');		       width--;		       }		       printf("%c", va_arg(pvar, char));		       }		       break;		       }		     */a355 2a356 1a383 1d409 1d415 5d423 1a423 1    if (i < 0)d425 1a432 1a484 1@

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -