Exemplo n.º 1
0
int i2c_open_device(const char* i2c_bus_name, char *filename, size_t size, int quiet)
{
	int i2cbus = lookup_i2c_bus(i2c_bus_name);
	int file = open_i2c_dev(i2cbus, filename, size, quiet);
	
	if(!quiet) printf("i2cbus=%d and dev=%s\n",i2cbus,filename);

	return file;
}
int main(int argc, char *argv[])
{
    int res, i2cbus, address, file;
    char filename[20];
    int force = 0;

    i2cbus = lookup_i2c_bus("1");
    printf("i2cbus = %d\n", i2cbus);
    if (i2cbus < 0)
        help();

    address = parse_i2c_address("0x70");
    printf("address = 0x%2x\n", address);
    if (address < 0)
        help();

    file = open_i2c_dev(i2cbus, filename, sizeof(filename), 0);
//	printf("file = %d\n", file);
    if (file < 0
            || check_funcs(file)
            || set_slave_addr(file, address, force))
        exit(1);

    // Check the return value on these if there is trouble
    i2c_smbus_write_byte(file, 0x21); // Start oscillator (p10)
    i2c_smbus_write_byte(file, 0x81); // Disp on, blink off (p11)
    i2c_smbus_write_byte(file, 0xe7); // Full brightness (page 15)

//	Display a series of pictures
    write_block(file, frown_bmp);
    sleep(1);
    write_block(file, neutral_bmp);
    sleep(1);
    write_block(file, smile_bmp);


// Fade the display
    int daddress;
    for(daddress = 0xef; daddress >= 0xe0; daddress--) {
//	    printf("writing: 0x%02x\n", daddress);
        res = i2c_smbus_write_byte(file, daddress);
        usleep(100000);	// Sleep 0.1 seconds
    }

    if (res < 0) {
        fprintf(stderr, "Error: Write failed\n");
        close(file);
        exit(1);
    }
    exit(0);
}
Exemplo n.º 3
0
int main(int argc, char *argv[])
{
	char *end;
	int res, i2cbus, address, size, file;
	int value, daddress, vmask = 0;
	int e1;
	char filename[20];
	long funcs;
	int pec = 0;
	int flags = 0;
	int yes = 0, version = 0;

	/* handle (optional) flags first */
	while (1+flags < argc && argv[1+flags][0] == '-') {
		switch (argv[1+flags][1]) {
		case 'V': version = 1; break;
		case 'y': yes = 1; break;
		default:
			fprintf(stderr, "Warning: Unsupported flag "
				"\"-%c\"!\n", argv[1+flags][1]);
			help();
			exit(1);
		}
		flags++;
	}

	if (version) {
		fprintf(stderr, "i2cset version %s\n", LM_VERSION);
		exit(0);
	}

	if (argc < flags + 5)
		help();

	i2cbus = strtol(argv[flags+1], &end, 0);
	if (*end || i2cbus < 0 || i2cbus > 0x3f) {
		fprintf(stderr, "Error: I2CBUS argument invalid!\n");
		help();
	}

	address = strtol(argv[flags+2], &end, 0);
	if (*end || address < 0 || address > 0x7f) {
		fprintf(stderr, "Error: Chip address invalid!\n");
		help();
	}

	daddress = strtol(argv[flags+3], &end, 0);
	if (*end || daddress < 0 || daddress > 0xff) {
		fprintf(stderr, "Error: Data address invalid!\n");
		help();
	}

	value = strtol(argv[flags+4], &end, 0);
	if (*end) {
		fprintf(stderr, "Error: Data value invalid!\n");
		help();
	}

	if (argc < flags + 6) {
		fprintf(stderr, "No size specified (using byte-data access)\n");
		size = I2C_SMBUS_BYTE_DATA;
	} else if (argv[flags+5][0] == 'b') {
		size = I2C_SMBUS_BYTE_DATA;
		pec = argv[flags+5][1] == 'p';
	} else if (argv[flags+5][0] == 'w') {
		size = I2C_SMBUS_WORD_DATA;
		pec = argv[flags+5][1] == 'p';
	} else {
		fprintf(stderr, "Error: Invalid mode!\n");
		help();
	}

	if (argc >= flags + 7) {
		vmask = strtol(argv[flags+6], &end, 0);
		if (*end || vmask == 0) {
			fprintf(stderr, "Error: Data value mask invalid!\n");
			help();
		}
	}

	if (value < 0
	 || (size == I2C_SMBUS_BYTE_DATA && value > 0xff)
	 || (size == I2C_SMBUS_WORD_DATA && value > 0xffff)) {
		fprintf(stderr, "Error: Data value out of range!\n");
		help();
	}

	file = open_i2c_dev(i2cbus, filename, 0);
	if (file < 0) {
		exit(1);
	}

	/* check adapter functionality */
	if (ioctl(file, I2C_FUNCS, &funcs) < 0) {
		fprintf(stderr, "Error: Could not get the adapter "
		        "functionality matrix: %s\n", strerror(errno));
		exit(1);
	}

	switch (size) {
	case I2C_SMBUS_BYTE_DATA:
		if (!(funcs & I2C_FUNC_SMBUS_WRITE_BYTE_DATA)) {
			fprintf(stderr, "Error: Adapter for i2c bus %d does "
			        "not have byte write capability\n", i2cbus);
			exit(1);
		}
		break;

	case I2C_SMBUS_WORD_DATA:
		if (!(funcs & I2C_FUNC_SMBUS_WRITE_WORD_DATA)) {
			fprintf(stderr, "Error: Adapter for i2c bus %d does "
			        "not have word write capability\n", i2cbus);
			exit(1);
		}
		break;
	}

	/* use FORCE so that we can write registers even when
	   a driver is also running */
	if (ioctl(file, I2C_SLAVE_FORCE, address) < 0) {
		fprintf(stderr, "Error: Could not set address to %d: %s\n",
		        address, strerror(errno));
		exit(1);
	}

	if (!yes) {
		char s[2];
		int dont = 0;

		fprintf(stderr, "WARNING! This program can confuse your I2C "
		        "bus, cause data loss and worse!\n");

		if (address >= 0x50 && address <= 0x57) {
			fprintf(stderr, "DANGEROUS! Writing to a serial "
			        "EEPROM on a memory DIMM\nmay render your "
			        "memory USELESS and make your system "
			        "UNBOOTABLE!\n");
			dont = 1;
		}

		fprintf(stderr, "I will write to device file %s, chip address "
		        "0x%02x, data address\n0x%02x, data 0x%02x%s, mode "
		        "%s.\n", filename, address, daddress, value,
			vmask ? " (masked)" : "",
			size == I2C_SMBUS_BYTE_DATA ? "byte" : "word");
		if (pec)
			fprintf(stderr, "PEC checking enabled.\n");

		fprintf(stderr, "Continue? [%s] ", dont ? "y/N" : "Y/n");
		fflush(stderr);
		fgets(s, 2, stdin);
		if ((s[0] != '\n' || dont) && s[0] != 'y' && s[0] != 'Y') {
			fprintf(stderr, "Aborting on user request.\n");
			exit(0);
		}
	}

	if (vmask) {
		int oldvalue;

		if (size == I2C_SMBUS_WORD_DATA) {
			oldvalue = i2c_smbus_read_word_data(file, daddress);
		} else {
			oldvalue = i2c_smbus_read_byte_data(file, daddress);
		}

		if (oldvalue < 0) {
			fprintf(stderr, "Error: Failed to read old value\n");
			exit(1);
		}

		value = (value & vmask) | (oldvalue & ~vmask);

		if (!yes) {
			char s[2];
			
			fprintf(stderr, "Old value 0x%0*x, write mask "
				"0x%0*x: Will write 0x%0*x to register "
				"0x%02x\n",
				size == I2C_SMBUS_WORD_DATA ? 4 : 2, oldvalue,
				size == I2C_SMBUS_WORD_DATA ? 4 : 2, vmask,
				size == I2C_SMBUS_WORD_DATA ? 4 : 2, value,
				daddress);

			fprintf(stderr, "Continue? [Y/n] ");
			fflush(stderr);
			fgets(s, 2, stdin);
			if (s[0] != '\n' && s[0] != 'y' && s[0] != 'Y') {
				fprintf(stderr, "Aborting on user request.\n");
				exit(0);
			}
		}
	}

	if (pec) {
		if (ioctl(file, I2C_PEC, 1) < 0) {
			fprintf(stderr, "Error: Could not set PEC: %s\n",
			        strerror(errno));
			exit(1);
		}
		if (!(funcs & (I2C_FUNC_SMBUS_HWPEC_CALC | I2C_FUNC_I2C))) {
			fprintf(stderr, "Warning: Adapter for i2c bus %d does "
			        "not seem to actually support PEC\n", i2cbus);
		}
	}

	e1 = 0;
	if (size == I2C_SMBUS_WORD_DATA) {
		res = i2c_smbus_write_word_data(file, daddress, value);
	} else {
		res = i2c_smbus_write_byte_data(file, daddress, value);
	}
	if (res < 0) {
		fprintf(stderr, "Warning - write failed\n");
		e1++;
	}

	if (pec) {
		if (ioctl(file, I2C_PEC, 0) < 0) {
			fprintf(stderr, "Error: Could not clear PEC: %s\n",
				strerror(errno));
			close(file);
			exit(e1);
		}
	}

	if (size == I2C_SMBUS_WORD_DATA) {
		res = i2c_smbus_read_word_data(file, daddress);
	} else {
		res = i2c_smbus_read_byte_data(file, daddress);
	}
	close(file);

	if (res < 0) {
		fprintf(stderr, "Warning - readback failed\n");
		e1++;
	} else
	if (res != value) {
		e1++;
		fprintf(stderr, "Warning - data mismatch - wrote "
		        "0x%0*x, read back 0x%0*x\n",
		        size == I2C_SMBUS_WORD_DATA ? 4 : 2, value,
		        size == I2C_SMBUS_WORD_DATA ? 4 : 2, res);
	} else {
		fprintf(stderr, "Value 0x%0*x written, readback matched\n",
		        size == I2C_SMBUS_WORD_DATA ? 4 : 2, value);
	}

	exit(e1);
}
Exemplo n.º 4
0
int main(int argc, char **argv, char **envp)
{
	struct pollfd fdset[7];
	int nfds = 7;
	int gpio_fd1, gpio_fd2, gpio_fd3, gpio_fd4,gpio_fd5,gpio_fd6, timeout, rc;
	char buf[MAX_BUF];
	unsigned int gpio;
	int len;
	char board[HEIGHT][WIDTH];
	int xpos=WIDTH/2;
	int ypos=HEIGHT/2;
        int row;
	int col;
	int colorint=0;
	char color[]={'x','y','z'};	
	for(row=0;row<HEIGHT;row++){
		printf("\n");
		for(col=0;col<WIDTH;col++){
			board[row][col]=' ';
		}
	}

	int res, i2cbus, address, file;
	char filename[20];
	int force = 0;

	i2cbus = lookup_i2c_bus("1");
	printf("i2cbus = %d\n", i2cbus);
	if (i2cbus < 0)
		help();

	address = parse_i2c_address("0x70");
	printf("address = 0x%2x\n", address);
	if (address < 0)
		help();

	file = open_i2c_dev(i2cbus, filename, sizeof(filename), 0);
//	printf("file = %d\n", file);
	if (file < 0
	 || check_funcs(file)
	 || set_slave_addr(file, address, force))
		exit(1);

	// Check the return value on these if there is trouble
	i2c_smbus_write_byte(file, 0x21); // Start oscillator (p10)
	i2c_smbus_write_byte(file, 0x81); // Disp on, blink off (p11)
	i2c_smbus_write_byte(file, 0xe7); // Full brightness (page 15)

//	Display a series of pictures
	

	system("/home/root/homework3/i2csetup.sh");
	board[xpos][ypos]='x';
	printboard(board,file,colorint);
	//printf("wgat");
	/*if (argc < 2) {
		printf("Usage: gpio-int <gpio-pin>\n\n");
		printf("Waits for a change in the GPIO pin voltage level or input on stdin\n");


		FILE* f = fopen("/sys/class/leds/beaglebone\:green\:usr0/brightness", "w");
                FILE* trig = fopen("/sys/class/leds/beaglebone\:green\:usr0/trigger", "w");
 
    		if (trig == NULL){
			printf("oops\n");        			
			exit(EXIT_FAILURE);
		}
    		fprintf(trig, "none");
    		fclose(trig);
		if (fled== NULL){
			printf("oops\n");        			
			exit(EXIT_FAILURE);
		}
		printf("should light up\n");
    		fprintf(fled, "1");
    		fclose(fled);
		usleep(10000000);
		exit(-1);
	}
		*/
	// Set the signal callback for Ctrl-C
	signal(SIGINT, signal_handler);


	gpio_export(GPIOIN1);
	gpio_set_dir(GPIOIN1, "in");
	gpio_set_edge(GPIOIN1, "both");  // Can be rising, falling or both
	gpio_fd1 = gpio_fd_open(GPIOIN1, O_RDONLY);

	gpio_export(GPIOIN2);
	gpio_set_dir(GPIOIN2, "in");
	gpio_set_edge(GPIOIN2, "both");  // Can be rising, falling or both
	gpio_fd2 = gpio_fd_open(GPIOIN2, O_RDONLY);
	gpio_export(GPIOIN3);
	gpio_set_dir(GPIOIN3, "in");
	gpio_set_edge(GPIOIN3, "both");  // Can be rising, falling or both
	gpio_fd3 = gpio_fd_open(GPIOIN3, O_RDONLY);

	gpio_export(GPIOIN4);
	gpio_set_dir(GPIOIN4, "in");
	gpio_set_edge(GPIOIN4, "both");  // Can be rising, falling or both
	gpio_fd4 = gpio_fd_open(GPIOIN4, O_RDONLY);

	gpio_export(GPIOIN5);
	gpio_set_dir(GPIOIN5, "in");
	gpio_set_edge(GPIOIN5, "both");  // Can be rising, falling or both
	gpio_fd5 = gpio_fd_open(GPIOIN5, O_RDONLY);

	gpio_export(GPIOIN6);
	gpio_set_dir(GPIOIN6, "in");
	gpio_set_edge(GPIOIN6, "both");  // Can be rising, falling or both
	gpio_fd6 = gpio_fd_open(GPIOIN6, O_RDONLY);

	timeout = POLL_TIMEOUT;
 	FILE* f0 = fopen("/sys/class/leds/beaglebone:green:usr0/trigger", "w");
	FILE* f1 = fopen("/sys/class/leds/beaglebone:green:usr1/trigger", "w");
	FILE* f2 = fopen("/sys/class/leds/beaglebone:green:usr2/trigger", "w");
	FILE* f3 = fopen("/sys/class/leds/beaglebone:green:usr3/trigger", "w");

    	if (f0 == NULL){
		exit(EXIT_FAILURE);
	}
	fprintf(f0, "none");
	fclose(f0);

	if (f1 == NULL){
		exit(EXIT_FAILURE);
	}
	fprintf(f1, "none");
	fclose(f1);

	if (f2 == NULL){
		exit(EXIT_FAILURE);
	}
	fprintf(f2, "none");
	fclose(f2);
	
	if (f3 == NULL){
		exit(EXIT_FAILURE);
	}
	fprintf(f3, "none");
	fclose(f3);
	
			
	while (keepgoing) {
		memset((void*)fdset, 0, sizeof(fdset));
		
		fdset[0].fd = STDIN_FILENO;
		fdset[0].events = POLLIN;
      
		fdset[1].fd = gpio_fd1;
		fdset[1].events = POLLPRI;

		fdset[2].fd = gpio_fd2;
		fdset[2].events = POLLPRI;

		fdset[3].fd = gpio_fd3;
		fdset[3].events = POLLPRI;

		fdset[4].fd = gpio_fd4;
		fdset[4].events = POLLPRI;

		fdset[5].fd = gpio_fd5;
		fdset[5].events = POLLPRI;

		fdset[6].fd = gpio_fd6;
		fdset[6].events = POLLPRI;


		rc = poll(fdset, nfds, timeout);      

		if (rc < 0) {
			printf("\npoll() failed!\n");
			return -1;
		}
      
		
            
		if (fdset[1].revents & POLLPRI) {
			lseek(fdset[1].fd, 0, SEEK_SET);  // Read from the start of the file
			read(fdset[1].fd, buf, MAX_BUF);
			FILE* f = fopen("/sys/class/leds/beaglebone:green:usr3/brightness", "w");
 
    			if (f == NULL){        			
				exit(EXIT_FAILURE);
			}
			if (buf[0]=='1'){
				fprintf(f, "0");
			}
			if (buf[0]=='0'){
				fprintf(f, "1");
				if((xpos+1)<WIDTH){
					board[xpos+1][ypos]='x';
					xpos++;
				}
				printboard(board,file,colorint);
			}
			fclose(f);
				
		}
		if (fdset[2].revents & POLLPRI) {
			lseek(fdset[2].fd, 0, SEEK_SET);  // Read from the start of the file
			read(fdset[2].fd, buf, MAX_BUF);
			FILE* f = fopen("/sys/class/leds/beaglebone:green:usr2/brightness", "w");
 
    			if (f == NULL){        			
				exit(EXIT_FAILURE);
			}
			if (buf[0]=='1'){
				fprintf(f, "0");
			}
			if (buf[0]=='0'){
				fprintf(f, "1");
				if((xpos-1)>=0){
					board[xpos-1][ypos]='x';
					xpos--;
				}
				
				printboard(board,file,colorint);

			}
			fclose(f);
				
		}
		if (fdset[3].revents & POLLPRI) {
			lseek(fdset[3].fd, 0, SEEK_SET);  // Read from the start of the file
			read(fdset[3].fd, buf, MAX_BUF);
			FILE* f = fopen("/sys/class/leds/beaglebone:green:usr1/brightness", "w");
 
    			if (f == NULL){        			
				exit(EXIT_FAILURE);
			}
			if (buf[0]=='1'){
				fprintf(f, "0");
			}
			if (buf[0]=='0'){
				if((ypos+1)<HEIGHT){
					board[xpos][ypos+1]='x';
					ypos++;
				}
				printboard(board,file,colorint);
				fprintf(f, "1");
			}
			fclose(f);
				
		}
		if (fdset[4].revents & POLLPRI) {
			lseek(fdset[4].fd, 0, SEEK_SET);  // Read from the start of the file
			read(fdset[4].fd, buf, MAX_BUF);
			FILE* f = fopen("/sys/class/leds/beaglebone:green:usr0/brightness", "w");
 
    			if (f == NULL){        			
				exit(EXIT_FAILURE);
			}
			if (buf[0]=='1'){
				fprintf(f, "0");
			}
			if (buf[0]=='0'){
				if((ypos-1)>=0){
					board[xpos][ypos-1]='x';
					ypos--;
				}
				printboard(board,file,colorint);
				fprintf(f, "1");

			}
			fclose(f);
				
		}
		if (fdset[5].revents & POLLPRI) {
			lseek(fdset[5].fd, 0, SEEK_SET);  // Read from the start of the file
			read(fdset[5].fd, buf, MAX_BUF);
			
			if (buf[0]=='0'){
				for(row=0;row<HEIGHT;row++){
				printf("\n");
					for(col=0;col<WIDTH;col++){
						board[row][col]=' ';
					}
					printf("\n");
					system("i2cget -y 1 0x48 0");
					printboard(board,file,colorint);
				}
				
				

			}
			
				
		}
		if (fdset[6].revents & POLLPRI) {
			lseek(fdset[6].fd, 0, SEEK_SET);  // Read from the start of the file
			read(fdset[6].fd, buf, MAX_BUF);
			
			if (buf[0]=='0'){
				if(colorint<=0){
					colorint++;
				}else{
					colorint=0;
				}
				printf("\n");
				system("i2cget -y 1 0x4a 0");
				printboard(board,file,colorint);

			}
			
			
			
				
		}
		/*if (fdset[0].revents & POLLIN) {
			(void)read(fdset[0].fd, buf, 1);
			printf("\npoll() stdin read 0x%2.2X\n", (unsigned int) buf[0]);
		}*/
		
		
		
		fflush(stdout);
	}
	
	
	gpio_fd_close(gpio_fd1);
	gpio_fd_close(gpio_fd2);
	gpio_fd_close(gpio_fd3);
	gpio_fd_close(gpio_fd4);
	return 0;
}
Exemplo n.º 5
0
int main(int argc, char *argv[])
{
	int res, i2cbus, address, size, file;
	int value, daddress;
	char filename[20];
	int force = 0, readback = 1;
	__u16 block[I2C_SMBUS_BLOCK_MAX];
	int len;

	i2cbus = lookup_i2c_bus("3");
	printf("i2cbus = %d\n", i2cbus);
	if (i2cbus < 0)
		help();

	address = parse_i2c_address("0x70");
	printf("address = 0x%2x\n", address);
	if (address < 0)
		help();

	size = I2C_SMBUS_BYTE;

	daddress = 0x21;
	if (daddress < 0 || daddress > 0xff) {
		fprintf(stderr, "Error: Data address invalid!\n");
		help();
	}

	file = open_i2c_dev(i2cbus, filename, sizeof(filename), 0);
	printf("file = %d\n", file);
	if (file < 0
		|| check_funcs(file, size)
		|| set_slave_addr(file, address, force))
		exit(1);


	switch (size) {
	case I2C_SMBUS_BYTE:
		daddress = 0x21; // Start oscillator (page 10)
		printf("writing: 0x%02x\n", daddress);
		res = i2c_smbus_write_byte(file, daddress);

		daddress = 0x81; // Display on, blinking off (page 11)
		printf("writing: 0x%02x\n", daddress);
		res = i2c_smbus_write_byte(file, daddress);

		daddress = 0xe7; // Full brightness (page 15)
		printf("writing: 0x%02x\n", daddress);
		res = i2c_smbus_write_byte(file, daddress);

		daddress = 0x00; // Start writing to address 0 (page 13)
		printf("writing: 0x%02x\n", daddress);
		res = i2c_smbus_write_byte(file, daddress);

		int i;

		displayImage(smile_bmp,res, daddress, file);
		displayImage(frown_bmp,res, daddress, file);
		displayImage(neutral_bmp,res, daddress, file);
		displayImage(my_bmp,res, daddress, file);
		sleep(4);
		

		// Closing file and turning off Matrix
		printf("Closing file and turning off the LED Matrix\n");
		daddress = 0x20;		
		//for(daddress = 0xef; daddress >= 0xe0; daddress--) {
		printf("writing: 0x%02x\n", daddress);
		res = i2c_smbus_write_byte(file, daddress);

		usleep(500000); // Sleep 0.5 seconds
		

		break;

	case I2C_SMBUS_WORD_DATA:
		res = i2c_smbus_write_word_data(file, daddress, value);
		break;
	case I2C_SMBUS_BLOCK_DATA:
		res = i2c_smbus_write_block_data(file, daddress, len, (const __u8 *)block);
		break;
	case I2C_SMBUS_I2C_BLOCK_DATA:
		res = i2c_smbus_write_i2c_block_data(file, daddress, len, (const __u8 *)block);
		break;
	default: /* I2C_SMBUS_BYTE_DATA */
		res = i2c_smbus_write_byte_data(file, daddress, value);
		break;
	}
	if (res < 0) {
		fprintf(stderr, "Error: Write failed\n");
		close(file);
		exit(1);
		}

	if (!readback) { /* We're done */
		close(file);
		exit(0);
		}

	switch (size) {
		case I2C_SMBUS_BYTE:
			res = i2c_smbus_read_byte(file);
			value = daddress;
			break;
		case I2C_SMBUS_WORD_DATA:
			res = i2c_smbus_read_word_data(file, daddress);
			break;
		default: /* I2C_SMBUS_BYTE_DATA */
			res = i2c_smbus_read_byte_data(file, daddress);
			}
	close(file);

	exit(0);
}
Exemplo n.º 6
0
int main(int argc, char *argv[])
{
	char *end;
	const char *maskp = NULL;
	int res, i2cbus, address, size, file;
	int value, daddress, vmask = 0;
	char filename[20];
	int pec = 0;
	int flags = 0;
	int force = 0, yes = 0, version = 0, readback = 0;
	unsigned char block[I2C_SMBUS_BLOCK_MAX];
	int len;

	/* handle (optional) flags first */
	while (1+flags < argc && argv[1+flags][0] == '-') {
		switch (argv[1+flags][1]) {
		case 'V': version = 1; break;
		case 'f': force = 1; break;
		case 'y': yes = 1; break;
		case 'm':
			if (2+flags < argc)
				maskp = argv[2+flags];
			flags++;
			break;
		case 'r': readback = 1; break;
		default:
			fprintf(stderr, "Error: Unsupported option "
				"\"%s\"!\n", argv[1+flags]);
			help();
			exit(1);
		}
		flags++;
	}

	if (version) {
		fprintf(stderr, "i2cset version %s\n", VERSION);
		exit(0);
	}

	if (argc < flags + 4)
		help();

	i2cbus = lookup_i2c_bus(argv[flags+1]);
	if (i2cbus < 0)
		help();

	address = parse_i2c_address(argv[flags+2]);
	if (address < 0)
		help();

	daddress = strtol(argv[flags+3], &end, 0);
	if (*end || daddress < 0 || daddress > 0xff) {
		fprintf(stderr, "Error: Data address invalid!\n");
		help();
	}

	/* check for command/mode */
	if (argc == flags + 4) {
		/* Implicit "c" */
		size = I2C_SMBUS_BYTE;
	} else if (argc == flags + 5) {
		/* "c", "cp",  or implicit "b" */
		if (!strcmp(argv[flags+4], "c")
		 || !strcmp(argv[flags+4], "cp")) {
			size = I2C_SMBUS_BYTE;
			pec = argv[flags+4][1] == 'p';
		} else {
			size = I2C_SMBUS_BYTE_DATA;
		}
	} else {
		/* All other commands */
		if (strlen(argv[argc-1]) > 2
		    || (strlen(argv[argc-1]) == 2 && argv[argc-1][1] != 'p')) {
			fprintf(stderr, "Error: Invalid mode '%s'!\n", argv[argc-1]);
			help();
		}
		switch (argv[argc-1][0]) {
		case 'b': size = I2C_SMBUS_BYTE_DATA; break;
		case 'w': size = I2C_SMBUS_WORD_DATA; break;
		case 's': size = I2C_SMBUS_BLOCK_DATA; break;
		case 'i': size = I2C_SMBUS_I2C_BLOCK_DATA; break;
		default:
			fprintf(stderr, "Error: Invalid mode '%s'!\n", argv[argc-1]);
			help();
		}
		pec = argv[argc-1][1] == 'p';
		if (size == I2C_SMBUS_BLOCK_DATA || size == I2C_SMBUS_I2C_BLOCK_DATA) {
			if (pec && size == I2C_SMBUS_I2C_BLOCK_DATA) {
				fprintf(stderr, "Error: PEC not supported for I2C block writes!\n");
				help();
			}
			if (maskp) {
				fprintf(stderr, "Error: Mask not supported for block writes!\n");
				help();
			}
			if (argc > (int)sizeof(block) + flags + 5) {
				fprintf(stderr, "Error: Too many arguments!\n");
				help();
			}
		} else if (argc != flags + 6) {
			fprintf(stderr, "Error: Too many arguments!\n");
			help();
		}
	}

	len = 0; /* Must always initialize len since it is passed to confirm() */

	/* read values from command line */
	switch (size) {
	case I2C_SMBUS_BYTE_DATA:
	case I2C_SMBUS_WORD_DATA:
		value = strtol(argv[flags+4], &end, 0);
		if (*end || value < 0) {
			fprintf(stderr, "Error: Data value invalid!\n");
			help();
		}
		if ((size == I2C_SMBUS_BYTE_DATA && value > 0xff)
		    || (size == I2C_SMBUS_WORD_DATA && value > 0xffff)) {
			fprintf(stderr, "Error: Data value out of range!\n");
			help();
		}
		break;
	case I2C_SMBUS_BLOCK_DATA:
	case I2C_SMBUS_I2C_BLOCK_DATA:
		for (len = 0; len + flags + 5 < argc; len++) {
			value = strtol(argv[flags + len + 4], &end, 0);
			if (*end || value < 0) {
				fprintf(stderr, "Error: Data value invalid!\n");
				help();
			}
			if (value > 0xff) {
				fprintf(stderr, "Error: Data value out of range!\n");
				help();
			}
			block[len] = value;
		}
		value = -1;
		break;
	default:
		value = -1;
		break;
	}

	if (maskp) {
		vmask = strtol(maskp, &end, 0);
		if (*end || vmask == 0) {
			fprintf(stderr, "Error: Data value mask invalid!\n");
			help();
		}
		if (((size == I2C_SMBUS_BYTE || size == I2C_SMBUS_BYTE_DATA)
		     && vmask > 0xff) || vmask > 0xffff) {
			fprintf(stderr, "Error: Data value mask out of range!\n");
			help();
		}
	}

	file = open_i2c_dev(i2cbus, filename, sizeof(filename), 0);
	if (file < 0
	 || check_funcs(file, size, pec)
	 || set_slave_addr(file, address, force))
		exit(1);

	if (!yes && !confirm(filename, address, size, daddress,
			     value, vmask, block, len, pec))
		exit(0);

	if (vmask) {
		int oldvalue;

		switch (size) {
		case I2C_SMBUS_BYTE:
			oldvalue = i2c_smbus_read_byte(file);
			break;
		case I2C_SMBUS_WORD_DATA:
			oldvalue = i2c_smbus_read_word_data(file, daddress);
			break;
		default:
			oldvalue = i2c_smbus_read_byte_data(file, daddress);
		}

		if (oldvalue < 0) {
			fprintf(stderr, "Error: Failed to read old value\n");
			exit(1);
		}

		value = (value & vmask) | (oldvalue & ~vmask);

		if (!yes) {
			fprintf(stderr, "Old value 0x%0*x, write mask "
				"0x%0*x: Will write 0x%0*x to register "
				"0x%02x\n",
				size == I2C_SMBUS_WORD_DATA ? 4 : 2, oldvalue,
				size == I2C_SMBUS_WORD_DATA ? 4 : 2, vmask,
				size == I2C_SMBUS_WORD_DATA ? 4 : 2, value,
				daddress);

			fprintf(stderr, "Continue? [Y/n] ");
			fflush(stderr);
			if (!user_ack(1)) {
				fprintf(stderr, "Aborting on user request.\n");
				exit(0);
			}
		}
	}

	if (pec && ioctl(file, I2C_PEC, 1) < 0) {
		fprintf(stderr, "Error: Could not set PEC: %s\n",
			strerror(errno));
		close(file);
		exit(1);
	}

	switch (size) {
	case I2C_SMBUS_BYTE:
		res = i2c_smbus_write_byte(file, daddress);
		break;
	case I2C_SMBUS_WORD_DATA:
		res = i2c_smbus_write_word_data(file, daddress, value);
		break;
	case I2C_SMBUS_BLOCK_DATA:
		res = i2c_smbus_write_block_data(file, daddress, len, block);
		break;
	case I2C_SMBUS_I2C_BLOCK_DATA:
		res = i2c_smbus_write_i2c_block_data(file, daddress, len, block);
		break;
	default: /* I2C_SMBUS_BYTE_DATA */
		res = i2c_smbus_write_byte_data(file, daddress, value);
		break;
	}
	if (res < 0) {
		fprintf(stderr, "Error: Write failed\n");
		close(file);
		exit(1);
	}

	if (pec) {
		if (ioctl(file, I2C_PEC, 0) < 0) {
			fprintf(stderr, "Error: Could not clear PEC: %s\n",
				strerror(errno));
			close(file);
			exit(1);
		}
	}

	if (!readback) { /* We're done */
		close(file);
		exit(0);
	}

	switch (size) {
	case I2C_SMBUS_BYTE:
		res = i2c_smbus_read_byte(file);
		value = daddress;
		break;
	case I2C_SMBUS_WORD_DATA:
		res = i2c_smbus_read_word_data(file, daddress);
		break;
	default: /* I2C_SMBUS_BYTE_DATA */
		res = i2c_smbus_read_byte_data(file, daddress);
	}
	close(file);

	if (res < 0) {
		printf("Warning - readback failed\n");
	} else
	if (res != value) {
		printf("Warning - data mismatch - wrote "
		       "0x%0*x, read back 0x%0*x\n",
		       size == I2C_SMBUS_WORD_DATA ? 4 : 2, value,
		       size == I2C_SMBUS_WORD_DATA ? 4 : 2, res);
	} else {
		printf("Value 0x%0*x written, readback matched\n",
		       size == I2C_SMBUS_WORD_DATA ? 4 : 2, value);
	}

	exit(0);
}
Exemplo n.º 7
0
int main(int argc, char *argv[])
{
	char *end;
	int i2cbus, file, res;
	char filename[20];
	long funcs;
	int mode = MODE_AUTO;
	int first = 0x03, last = 0x77;
	int flags = 0;
	int yes = 0, version = 0, list = 0;

	/* handle (optional) flags first */
	while (1+flags < argc && argv[1+flags][0] == '-') {
		switch (argv[1+flags][1]) {
		case 'V': version = 1; break;
		case 'y': yes = 1; break;
		case 'l': list = 1; break;
		case 'r': 
			if (mode == MODE_QUICK) {
				fprintf(stderr, "Error: Different modes "
				        "specified!\n");
				exit(1);
			}
			mode = MODE_READ;
			break;
		case 'q':
			if (mode == MODE_READ) {
				fprintf(stderr, "Error: Different modes "
				        "specified!\n");
				exit(1);
			}
			mode = MODE_QUICK;
			break;
		case 'a':
			first = 0x00;
			last = 0x7F;
			break;
		default:
			fprintf(stderr, "Warning: Unsupported flag "
				"\"-%c\"!\n", argv[1+flags][1]);
			help();
			exit(1);
		}
		flags++;
	}

	if (version) {
		fprintf(stderr, "i2cdetect version %s\n", LM_VERSION);
		exit(0);
	}

	if (list) {
		print_i2c_busses(1);
		exit(0);
	}

	if (argc < flags + 2) {
		fprintf(stderr, "Error: No i2c-bus specified!\n");
		help();
		exit(1);
	}
	i2cbus = strtol(argv[flags+1], &end, 0);
	if (*end) {
		fprintf(stderr, "Error: I2CBUS argument not a number!\n");
		help();
		exit(1);
	}
	if ((i2cbus < 0) || (i2cbus > 0xff)) {
		fprintf(stderr, "Error: I2CBUS argument out of range "
		        "(0-255)!\n");
		help();
		exit(1);
	}

	/* read address range if present */
	if (argc == flags + 4) {
		int tmp;

		tmp = strtol(argv[flags+2], &end, 0);
		if (*end) {
			fprintf(stderr, "Error: FIRST argment not a "
			        "number!\n");
			help();
			exit(1);
		}
		if (tmp < first || tmp > last) {
			fprintf(stderr, "Error: FIRST argument out of range "
			        "(0x%02x-0x%02x)!\n", first, last);
			help();
			exit(1);
		}
		first = tmp;

		tmp = strtol(argv[flags+3], &end, 0);
		if (*end) {
			fprintf(stderr, "Error: LAST argment not a "
			        "number!\n");
			help();
			exit(1);
		}
		if (tmp < first || tmp > last) {
			fprintf(stderr, "Error: LAST argument out of range "
			        "(0x%02x-0x%02x)!\n", first, last);
			help();
			exit(1);
		}
		last = tmp;
	} else if (argc != flags + 2) {
		help();
		exit(1);
	}

	file = open_i2c_dev(i2cbus, filename, 0);
	if (file < 0) {
		exit(1);
	}

	if (ioctl(file, I2C_FUNCS, &funcs) < 0) {
		fprintf(stderr, "Error: Could not get the adapter "
		        "functionality matrix: %s\n", strerror(errno));
		close(file);
		exit(1);
	}
	if (mode != MODE_READ && !(funcs & I2C_FUNC_SMBUS_QUICK)) {
		fprintf(stderr, "Error: Can't use SMBus Quick Write command "
		        "on this bus (ISA bus?)\n");
		close(file);
		exit(1);
	}
	if (mode != MODE_QUICK && !(funcs & I2C_FUNC_SMBUS_READ_BYTE)) {
		fprintf(stderr, "Error: Can't use SMBus Read Byte command "
		        "on this bus (ISA bus?)\n");
		close(file);
		exit(1);
	}

	if (!yes) {
		char s[2];

		fprintf(stderr, "WARNING! This program can confuse your I2C "
		        "bus, cause data loss and worse!\n");

		fprintf(stderr, "I will probe file %s%s.\n", filename,
		        mode==MODE_QUICK?" using quick write commands":
		        mode==MODE_READ?" using read byte commands":"");
		fprintf(stderr, "I will probe address range 0x%02x-0x%02x.\n",
		        first, last);

		fprintf(stderr, "Continue? [Y/n] ");
		fflush(stderr);
		fgets(s, 2, stdin);
		if (s[0] != '\n' && s[0] != 'y' && s[0] != 'Y') {
			fprintf(stderr, "Aborting on user request.\n");
			exit(0);
		}
	}

	res = scan_i2c_bus(file, mode, first, last);

	close(file);

	exit(res?1:0);
}
Exemplo n.º 8
0
int main(int argc, char *argv[])
{
	char *end;
	int res, i2cbus, address, size, file;
	int daddress;
	char filename[20];
	int pec = 0;
	int flags = 0;
	int force = 0, yes = 0, version = 0, extend = 0;
	char buf[2];// = {0x0,0x1};

	/* handle (optional) flags first */
	while (1+flags < argc && argv[1+flags][0] == '-') {
		switch (argv[1+flags][1]) {
		case 'V': version = 1; break;
		case 'f': force = 1; break;
		case 'y': yes = 1; break;
		case 'e': extend = 1; break;
		default:
			fprintf(stderr, "Error: Unsupported option "
				"\"%s\"!\n", argv[1+flags]);
			help();
			exit(1);
		}
		flags++;
	}

	if (version) {
		fprintf(stderr, "i2cget version %s\n", VERSION);
		exit(0);
	}

	if (argc < flags + 3)
		help();

	i2cbus = lookup_i2c_bus(argv[flags+1]);
	if (i2cbus < 0)
		help();

	address = parse_i2c_address(argv[flags+2]);
	if (address < 0)
		help();

	if (argc > flags + 3) {
		size = I2C_SMBUS_BYTE_DATA;
		daddress = strtol(argv[flags+3], &end, 0);
		if (*end || daddress < 0 || daddress > 0xff) {
			fprintf(stderr, "Error: Data address invalid!\n");
			help();
		}
	} else {
		size = I2C_SMBUS_BYTE;
		daddress = -1;
	}
	char *pEnd;
	if (extend) {
		buf[0] = strtol(argv[flags+3], &pEnd, 0);
		buf[1] = strtol(argv[flags+4], &pEnd, 0); 
		
		file = open_i2c_dev(i2cbus, filename, sizeof(filename), 0);
		address = parse_i2c_address(argv[flags+2]);
		
		two_byte_address_read(buf, file, address);
	}


	if (argc > flags + 4) {
		switch (argv[flags+4][0]) {
		case 'b': size = I2C_SMBUS_BYTE_DATA; break;
		case 'w': size = I2C_SMBUS_WORD_DATA; break;
		case 'c': size = I2C_SMBUS_BYTE; break;
		default:
			fprintf(stderr, "Error: Invalid mode!\n");
			help();
		}
		pec = argv[flags+4][1] == 'p';
	}

	file = open_i2c_dev(i2cbus, filename, sizeof(filename), 0);
	if (file < 0
	 || check_funcs(file, size, daddress, pec)
	 || set_slave_addr(file, address, force))
		exit(1);

	if (!yes && !confirm(filename, address, size, daddress, pec))
		exit(0);

	if (pec && ioctl(file, I2C_PEC, 1) < 0) {
		fprintf(stderr, "Error: Could not set PEC: %s\n",
			strerror(errno));
		close(file);
		exit(1);
	}

	switch (size) {
	case I2C_SMBUS_BYTE:
		if (daddress >= 0) {
			res = i2c_smbus_write_byte(file, daddress);
			if (res < 0)
				fprintf(stderr, "Warning - write failed\n");
		}
		res = i2c_smbus_read_byte(file);
		break;
	case I2C_SMBUS_WORD_DATA:
		res = i2c_smbus_read_word_data(file, daddress);
		break;
	default: /* I2C_SMBUS_BYTE_DATA */
		res = i2c_smbus_read_byte_data(file, daddress);
	}
	close(file);

	if (res < 0) {
		fprintf(stderr, "Error: Read failed\n");
		exit(2);
	}

	printf("0x%0*x\n", size == I2C_SMBUS_WORD_DATA ? 4 : 2, res);

	exit(0);
}
Exemplo n.º 9
0
int main(int argc, char *argv[])
{
	int i, j, res, i2cbus, address, size, file;
	int bank = 0;
	char filename[20];
	int block[256], s_length = 0;
	int pec = 0, even = 0;
	int force = 0;
	int first = 0x00, last = 0xff;

        char addr[6];
        int addrSize = sizeof(addr);
        int addrPos = 0;

	i2cbus = I2C_BUS_NUM;
	if (i2cbus < 0) {
		exit(1);
	}

	address = I2C_EEPROM_ADDR;
	if (address < 0) {
		exit(1);
	}
	size = I2C_SMBUS_BYTE_DATA;

	first = I2C_EEPROM_RANGE_FIRST;
	last = I2C_EEPROM_RANGE_LAST;

	file = open_i2c_dev(i2cbus, filename, sizeof(filename), 0);
	if (file < 0
	 || check_funcs(file, size, pec)
	 || set_slave_addr(file, address, force))
		exit(1);

	if (pec) {
		if (ioctl(file, I2C_PEC, 1) < 0) {
			fprintf(stderr, "Error: Could not set PEC: %s\n",
				strerror(errno));
			exit(1);
		}
	}

	/* handle all but word data */
	if (size != I2C_SMBUS_WORD_DATA || even) {
		/* do the block transaction */
		if (size == I2C_SMBUS_BLOCK_DATA
		 || size == I2C_SMBUS_I2C_BLOCK_DATA) {
			unsigned char cblock[288];

			if (size == I2C_SMBUS_BLOCK_DATA) {
				res = i2c_smbus_read_block_data(file, bank,
				      cblock);
			} else {
				for (res = 0; res < 256; res += i) {
					i = i2c_smbus_read_i2c_block_data(file,
						res, 32, cblock + res);
					if (i <= 0) {
						res = i;
						break;
					}
				}
			}
			if (res <= 0) {
				fprintf(stderr, "Error: Block read failed, "
					"return code %d\n", res);
				exit(1);
			}
			if (res >= 256)
				res = 256;
			for (i = 0; i < res; i++)
				block[i] = cblock[i];
			if (size != I2C_SMBUS_BLOCK_DATA)
				for (i = res; i < 256; i++)
					block[i] = -1;
		}

		if (size == I2C_SMBUS_BYTE) {
			res = i2c_smbus_write_byte(file, first);
			if(res != 0) {
				fprintf(stderr, "Error: Write start address "
					"failed, return code %d\n", res);
				exit(1);
			}
		}

		i = first;
		for (j = 0; j <= (last-first); j++) {
			fflush(stdout);
			/* Skip unwanted registers */
			if (i+j < first || i+j > last) {
				if (size == I2C_SMBUS_WORD_DATA) {
					j++;
				}
				continue;
			}

			if (size == I2C_SMBUS_BYTE_DATA) {
				block[i+j] = res =
					i2c_smbus_read_byte_data(file, i+j);
			} else if (size == I2C_SMBUS_WORD_DATA) {
				res = i2c_smbus_read_word_data(file,
						i+j);
				if (res < 0) {
					block[i+j] = res;
					block[i+j+1] = res;
				} else {
					block[i+j] = res & 0xff;
					block[i+j+1] = res >> 8;
				}
			} else if (size == I2C_SMBUS_BYTE) {
				block[i+j] = res =
					i2c_smbus_read_byte(file);
			} else
				res = block[i+j];

			if (size == I2C_SMBUS_BLOCK_DATA
					&& i+j >= s_length) {
				printf("   ");
			} else if (res < 0) {
				printf("XX ");
				if (size == I2C_SMBUS_WORD_DATA)
					printf("XX ");
			} else {
                                if(addrPos < addrSize)
                                {
                                  addr[addrPos] = block[i+j];
                                  addrPos++;
                                }
                                else
                                {
                                  fprintf(stderr, "ERROR: MAC Address buffer overflow\n");
                                  exit(1);
                                }
			}
			if (size == I2C_SMBUS_WORD_DATA)
				j++;
		}
Exemplo n.º 10
0
int main(int argc, char *argv[])
{
	char *end;
	const char *maskp = NULL;
	int res, i2cbus, address, size, file;
	int value, daddress, vmask = 0;
	char filename[20];
	int pec = 0;
	int flags = 0;
	int force = 0, yes = 0, version = 0, readback = 0;

	/* handle (optional) flags first */
	while (1+flags < argc && argv[1+flags][0] == '-') {
		switch (argv[1+flags][1]) {
		case 'V': version = 1; break;
		case 'f': force = 1; break;
		case 'y': yes = 1; break;
		case 'm':
			if (2+flags < argc)
				maskp = argv[2+flags];
			flags++;
			break;
		case 'r': readback = 1; break;
		default:
			fprintf(stderr, "Error: Unsupported option "
				"\"%s\"!\n", argv[1+flags]);
			help();
			exit(1);
		}
		flags++;
	}

	if (version) {
		fprintf(stderr, "i2cset version %s\n", VERSION);
		exit(0);
	}

	if (argc < flags + 4)
		help();

	i2cbus = lookup_i2c_bus(argv[flags+1]);
	if (i2cbus < 0)
		help();

	address = parse_i2c_address(argv[flags+2]);
	if (address < 0)
		help();

	daddress = strtol(argv[flags+3], &end, 0);
	if (*end || daddress < 0 || daddress > 0xff) {
		fprintf(stderr, "Error: Data address invalid!\n");
		help();
	}

	if (argc > flags + 4) {
		size = I2C_SMBUS_BYTE_DATA;
		value = strtol(argv[flags+4], &end, 0);
		if (*end || value < 0) {
			fprintf(stderr, "Error: Data value invalid!\n");
			help();
		}
	} else {
		size = I2C_SMBUS_BYTE;
		value = -1;
	}

	if (argc > flags + 5) {
		switch (argv[flags+5][0]) {
		case 'b': size = I2C_SMBUS_BYTE_DATA; break;
		case 'w': size = I2C_SMBUS_WORD_DATA; break;
		default:
			fprintf(stderr, "Error: Invalid mode!\n");
			help();
		}
		pec = argv[flags+5][1] == 'p';
	}

	/* Old method to provide the value mask, deprecated and no longer
	   documented but still supported for compatibility */
	if (argc > flags + 6) {
		if (maskp) {
			fprintf(stderr, "Error: Data value mask provided twice!\n");
			help();
		}
		fprintf(stderr, "Warning: Using deprecated way to set the data value mask!\n");
		fprintf(stderr, "         Please switch to using -m.\n");
		maskp = argv[flags+6];
	}

	if (maskp) {
		vmask = strtol(maskp, &end, 0);
		if (*end || vmask == 0) {
			fprintf(stderr, "Error: Data value mask invalid!\n");
			help();
		}
	}

	if ((size == I2C_SMBUS_BYTE_DATA && value > 0xff)
	 || (size == I2C_SMBUS_WORD_DATA && value > 0xffff)) {
		fprintf(stderr, "Error: Data value out of range!\n");
		help();
	}

	file = open_i2c_dev(i2cbus, filename, 0);
	if (file < 0
	 || check_funcs(file, size, pec)
	 || set_slave_addr(file, address, force))
		exit(1);

	if (!yes && !confirm(filename, address, size, daddress,
			     value, vmask, pec))
		exit(0);

	if (vmask) {
		int oldvalue;

		switch (size) {
		case I2C_SMBUS_BYTE:
			oldvalue = i2c_smbus_read_byte(file);
			break;
		case I2C_SMBUS_WORD_DATA:
			oldvalue = i2c_smbus_read_word_data(file, daddress);
			break;
		default:
			oldvalue = i2c_smbus_read_byte_data(file, daddress);
		}

		if (oldvalue < 0) {
			fprintf(stderr, "Error: Failed to read old value\n");
			exit(1);
		}

		value = (value & vmask) | (oldvalue & ~vmask);

		if (!yes) {
			fprintf(stderr, "Old value 0x%0*x, write mask "
				"0x%0*x: Will write 0x%0*x to register "
				"0x%02x\n",
				size == I2C_SMBUS_WORD_DATA ? 4 : 2, oldvalue,
				size == I2C_SMBUS_WORD_DATA ? 4 : 2, vmask,
				size == I2C_SMBUS_WORD_DATA ? 4 : 2, value,
				daddress);

			fprintf(stderr, "Continue? [Y/n] ");
			fflush(stderr);
			if (!user_ack(1)) {
				fprintf(stderr, "Aborting on user request.\n");
				exit(0);
			}
		}
	}

	if (pec && ioctl(file, I2C_PEC, 1) < 0) {
		fprintf(stderr, "Error: Could not set PEC: %s\n",
			strerror(errno));
		close(file);
		exit(1);
	}

	switch (size) {
	case I2C_SMBUS_BYTE:
		res = i2c_smbus_write_byte(file, daddress);
		break;
	case I2C_SMBUS_WORD_DATA:
		res = i2c_smbus_write_word_data(file, daddress, value);
		break;
	default: /* I2C_SMBUS_BYTE_DATA */
		res = i2c_smbus_write_byte_data(file, daddress, value);
	}
	if (res < 0) {
		fprintf(stderr, "Error: Write failed\n");
		close(file);
		exit(1);
	}

	if (pec) {
		if (ioctl(file, I2C_PEC, 0) < 0) {
			fprintf(stderr, "Error: Could not clear PEC: %s\n",
				strerror(errno));
			close(file);
			exit(1);
		}
	}

	if (!readback) { /* We're done */
		close(file);
		exit(0);
	}

	switch (size) {
	case I2C_SMBUS_BYTE:
		res = i2c_smbus_read_byte(file);
		value = daddress;
		break;
	case I2C_SMBUS_WORD_DATA:
		res = i2c_smbus_read_word_data(file, daddress);
		break;
	default: /* I2C_SMBUS_BYTE_DATA */
		res = i2c_smbus_read_byte_data(file, daddress);
	}
	close(file);

	if (res < 0) {
		printf("Warning - readback failed\n");
	} else
	if (res != value) {
		printf("Warning - data mismatch - wrote "
		       "0x%0*x, read back 0x%0*x\n",
		       size == I2C_SMBUS_WORD_DATA ? 4 : 2, value,
		       size == I2C_SMBUS_WORD_DATA ? 4 : 2, res);
	} else {
		printf("Value 0x%0*x written, readback matched\n",
		       size == I2C_SMBUS_WORD_DATA ? 4 : 2, value);
	}

	exit(0);
}
Exemplo n.º 11
0
int main(int argc, char *argv[])
{
	char *end;
	int res, i2cbus, address, size, file;
	int daddress;
	char filename[20];
	int pec = 0;
	int flags = 0;
	int force = 0, yes = 0, version = 0;

	/* handle (optional) flags first */
	while (1+flags < argc && argv[1+flags][0] == '-') {
		switch (argv[1+flags][1]) {
		case 'V': version = 1; break;
		case 'f': force = 1; break;
		case 'y': yes = 1; break;
		default:
			fprintf(stderr, "Error: Unsupported option "
				"\"%s\"!\n", argv[1+flags]);
			help();
			exit(1);
		}
		flags++;
	}

	if (version) {
		fprintf(stderr, "i2cget version %s\n", VERSION);
		exit(0);
	}

	if (argc < flags + 3)
		help();

	i2cbus = lookup_i2c_bus(argv[flags+1]);
	if (i2cbus < 0)
		help();

	address = parse_i2c_address(argv[flags+2]);
	if (address < 0)
		help();

	if (argc > flags + 3) {
		size = I2C_SMBUS_BYTE_DATA;
		daddress = strtol(argv[flags+3], &end, 0);
		if (*end || daddress < 0 || daddress > 0xff) {
			fprintf(stderr, "Error: Data address invalid!\n");
			help();
		}
	} else {
		size = I2C_SMBUS_BYTE;
		daddress = -1;
	}

	if (argc > flags + 4) {
		switch (argv[flags+4][0]) {
		case 'b': size = I2C_SMBUS_BYTE_DATA; break;
		case 'w': size = I2C_SMBUS_WORD_DATA; break;
		case 'c': size = I2C_SMBUS_BYTE; break;
		default:
			fprintf(stderr, "Error: Invalid mode!\n");
			help();
		}
		pec = argv[flags+4][1] == 'p';
	}

	file = open_i2c_dev(i2cbus, filename, sizeof(filename), 0);
	if (file < 0
	 || check_funcs(file, size, daddress, pec)
	 || set_slave_addr(file, address, force))
		exit(1);

	if (!yes && !confirm(filename, address, size, daddress, pec))
		exit(0);

	if (pec && ioctl(file, I2C_PEC, 1) < 0) {
		fprintf(stderr, "Error: Could not set PEC: %s\n",
			strerror(errno));
		close(file);
		exit(1);
	}

	switch (size) {
	case I2C_SMBUS_BYTE:
		if (daddress >= 0) {
#if 1
/*Use eepromer for large eeproms with two-byte addresses:*/
            __u8 buf[2] = { (daddress >> 8) & 0x0ff, daddress & 0x0ff};
/*            ioctl(file, BLKFLSBUF); // clear kernel read buffer*/
            res =i2c_smbus_write_byte_data(file, buf[0], buf[1]);
#else
/*Use eeprom for small eeproms with one-byte addresses:*/
/*            res = i2c_smbus_write_byte(file, daddress);*/
#endif
			if (res < 0)
				fprintf(stderr, "Warning - write failed\n");
		}
/*        ioctl(file, BLKFLSBUF); // clear kernel read buffer*/
		res = i2c_smbus_read_byte(file);
		break;
	case I2C_SMBUS_WORD_DATA:
        {
#if 1
/*Use eepromer for large eeproms with two-byte addresses:*/
/*            __u8 buf[2] = { (daddress >> 8) & 0x0ff, daddress & 0x0ff};*/
            __u8 buf[2] = { 0x00, 0x00};
/*            ioctl(file, BLKFLSBUF); // clear kernel read buffer*/
            res =i2c_smbus_write_byte_data(file, buf[0], buf[1]);
#endif
            res = i2c_smbus_read_word_data(file, daddress);
        }
		break;
	default: /* I2C_SMBUS_BYTE_DATA */
        {
#if 1
/*Use eepromer for large eeproms with two-byte addresses:*/
/*            __u8 buf[2] = { (daddress >> 8) & 0x0ff, daddress & 0x0ff};*/
            __u8 buf[2] = { 0x00, 0x00};
/*            ioctl(file, BLKFLSBUF); // clear kernel read buffer*/
            res =i2c_smbus_write_byte_data(file, buf[0], buf[1]);
#endif
            res = i2c_smbus_read_byte_data(file, daddress);
        }
	}
Exemplo n.º 12
0
int main(int argc, char *argv[])
{
	char *end;
	int i, j, res, i2cbus, address, size, file;
	int bank = 0, bankreg = 0x4E, old_bank = 0;
	char filename[20];
	int block[256], s_length = 0;
	int pec = 0, even = 0;
	int flags = 0;
	int force = 0, yes = 0, version = 0;
	const char *range = NULL;
	int first = 0x00, last = 0xff;

	/* handle (optional) flags first */
	while (1+flags < argc && argv[1+flags][0] == '-') {
		switch (argv[1+flags][1]) {
		case 'V': version = 1; break;
		case 'f': force = 1; break;
		case 'r': range = argv[1+(++flags)]; break;
		case 'y': yes = 1; break;
		default:
			fprintf(stderr, "Error: Unsupported option "
				"\"%s\"!\n", argv[1+flags]);
			help();
			exit(1);
		}
		flags++;
	}

	if (version) {
		fprintf(stderr, "i2cdump version %s\n", VERSION);
		exit(0);
	}

	if (argc < flags + 2) {
		fprintf(stderr, "Error: No i2c-bus specified!\n");
		help();
		exit(1);
	}
	i2cbus = lookup_i2c_bus(argv[flags+1]);
	if (i2cbus < 0) {
		help();
		exit(1);
	}

	if (argc < flags + 3) {
		fprintf(stderr, "Error: No address specified!\n");
		help();
		exit(1);
	}
	address = parse_i2c_address(argv[flags+2]);
	if (address < 0) {
		help();
		exit(1);
	}

	if (argc < flags + 4) {
		fprintf(stderr, "No size specified (using byte-data access)\n");
		size = I2C_SMBUS_BYTE_DATA;
	} else if (!strncmp(argv[flags+3], "b", 1)) {
		size = I2C_SMBUS_BYTE_DATA;
		pec = argv[flags+3][1] == 'p';
	} else if (!strncmp(argv[flags+3], "w", 1)) {
		size = I2C_SMBUS_WORD_DATA;
		pec = argv[flags+3][1] == 'p';
	} else if (!strncmp(argv[flags+3], "W", 1)) {
		size = I2C_SMBUS_WORD_DATA;
		even = 1;
	} else if (!strncmp(argv[flags+3], "s", 1)) {
		size = I2C_SMBUS_BLOCK_DATA;
		pec = argv[flags+3][1] == 'p';
	} else if (!strncmp(argv[flags+3], "c", 1)) {
		size = I2C_SMBUS_BYTE;
		pec = argv[flags+3][1] == 'p';
	} else if (!strcmp(argv[flags+3], "i"))
		size = I2C_SMBUS_I2C_BLOCK_DATA;
	else {
		fprintf(stderr, "Error: Invalid mode!\n");
		help();
		exit(1);
	}

	if (argc > flags + 4) {
		bank = strtol(argv[flags+4], &end, 0);
		if (*end || size == I2C_SMBUS_I2C_BLOCK_DATA) {
			fprintf(stderr, "Error: Invalid bank number!\n");
			help();
			exit(1);
		}
		if ((size == I2C_SMBUS_BYTE_DATA || size == I2C_SMBUS_WORD_DATA)
		 && (bank < 0 || bank > 15)) {
			fprintf(stderr, "Error: bank out of range!\n");
			help();
			exit(1);
		}
		if (size == I2C_SMBUS_BLOCK_DATA
		 && (bank < 0 || bank > 0xff)) {
			fprintf(stderr, "Error: block command out of range!\n");
			help();
			exit(1);
		}

		if (argc > flags + 5) {
			bankreg = strtol(argv[flags+5], &end, 0);
			if (*end || size == I2C_SMBUS_BLOCK_DATA) {
				fprintf(stderr, "Error: Invalid bank register "
					"number!\n");
				help();
				exit(1);
			}
			if (bankreg < 0 || bankreg > 0xff) {
				fprintf(stderr, "Error: bank out of range "
					"(0-0xff)!\n");
				help();
				exit(1);
			}
		}
	}

	/* Parse optional range string */
	if (range) {
		char *dash;

		first = strtol(range, &dash, 0);
		if (dash == range || *dash != '-'
		 || first < 0 || first > 0xff) {
			fprintf(stderr, "Error: Invalid range parameter!\n");
			exit(1);
		}
		last = strtol(++dash, &end, 0);
		if (end == dash || *end != '\0'
		 || last < first || last > 0xff) {
			fprintf(stderr, "Error: Invalid range parameter!\n");
			exit(1);
		}

		/* Check mode constraints */
		switch (size) {
		case I2C_SMBUS_BYTE:
		case I2C_SMBUS_BYTE_DATA:
			break;
		case I2C_SMBUS_WORD_DATA:
			if (!even || (!(first%2) && last%2))
				break;
			/* Fall through */
		default:
			fprintf(stderr,
				"Error: Range parameter not compatible with selected mode!\n");
			exit(1);
		}
	}

	file = open_i2c_dev(i2cbus, filename, sizeof(filename), 0);
	if (file < 0
	 || check_funcs(file, size, pec)
	 || set_slave_addr(file, address, force))
		exit(1);

	if (pec) {
		if (ioctl(file, I2C_PEC, 1) < 0) {
			fprintf(stderr, "Error: Could not set PEC: %s\n",
				strerror(errno));
			exit(1);
		}
	}

	if (!yes) {
		fprintf(stderr, "WARNING! This program can confuse your I2C "
			"bus, cause data loss and worse!\n");

		fprintf(stderr, "I will probe file %s, address 0x%x, mode "
			"%s\n", filename, address,
			size == I2C_SMBUS_BLOCK_DATA ? "smbus block" :
			size == I2C_SMBUS_I2C_BLOCK_DATA ? "i2c block" :
			size == I2C_SMBUS_BYTE ? "byte consecutive read" :
			size == I2C_SMBUS_BYTE_DATA ? "byte" : "word");
		if (pec)
			fprintf(stderr, "PEC checking enabled.\n");
		if (even)
			fprintf(stderr, "Only probing even register "
				"addresses.\n");
		if (bank) {
			if (size == I2C_SMBUS_BLOCK_DATA)
				fprintf(stderr, "Using command 0x%02x.\n",
					bank);
			else
				fprintf(stderr, "Probing bank %d using bank "
					"register 0x%02x.\n", bank, bankreg);
		}
		if (range) {
			fprintf(stderr,
				"Probe range limited to 0x%02x-0x%02x.\n",
				first, last);
		}

		fprintf(stderr, "Continue? [Y/n] ");
		fflush(stderr);
		if (!user_ack(1)) {
			fprintf(stderr, "Aborting on user request.\n");
			exit(0);
		}
	}

	/* See Winbond w83781d data sheet for bank details */
	if (bank && size != I2C_SMBUS_BLOCK_DATA) {
		res = i2c_smbus_read_byte_data(file, bankreg);
		if (res >= 0) {
			old_bank = res;
			res = i2c_smbus_write_byte_data(file, bankreg,
				bank | (old_bank & 0xf0));
		}
		if (res < 0) {
			fprintf(stderr, "Error: Bank switching failed\n");
			exit(1);
		}
	}

	/* handle all but word data */
	if (size != I2C_SMBUS_WORD_DATA || even) {
		/* do the block transaction */
		if (size == I2C_SMBUS_BLOCK_DATA
		 || size == I2C_SMBUS_I2C_BLOCK_DATA) {
			unsigned char cblock[288];

			if (size == I2C_SMBUS_BLOCK_DATA) {
				res = i2c_smbus_read_block_data(file, bank,
				      cblock);
				/* Remember returned block length for a nicer
				   display later */
				s_length = res;
			} else {
				for (res = 0; res < 256; res += i) {
					i = i2c_smbus_read_i2c_block_data(file,
						res, 32, cblock + res);
					if (i <= 0) {
						res = i;
						break;
					}
				}
			}
			if (res <= 0) {
				fprintf(stderr, "Error: Block read failed, "
					"return code %d\n", res);
				exit(1);
			}
			if (res >= 256)
				res = 256;
			for (i = 0; i < res; i++)
				block[i] = cblock[i];
			if (size != I2C_SMBUS_BLOCK_DATA)
				for (i = res; i < 256; i++)
					block[i] = -1;
		}

		if (size == I2C_SMBUS_BYTE) {
			res = i2c_smbus_write_byte(file, first);
			if(res != 0) {
				fprintf(stderr, "Error: Write start address "
					"failed, return code %d\n", res);
				exit(1);
			}
		}

		printf("     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f"
		       "    0123456789abcdef\n");
		for (i = 0; i < 256; i+=16) {
			if (size == I2C_SMBUS_BLOCK_DATA && i >= s_length)
				break;
			if (i/16 < first/16)
				continue;
			if (i/16 > last/16)
				break;

			printf("%02x: ", i);
			for (j = 0; j < 16; j++) {
				fflush(stdout);
				/* Skip unwanted registers */
				if (i+j < first || i+j > last) {
					printf("   ");
					if (size == I2C_SMBUS_WORD_DATA) {
						printf("   ");
						j++;
					}
					continue;
				}

				if (size == I2C_SMBUS_BYTE_DATA) {
					block[i+j] = res =
					  i2c_smbus_read_byte_data(file, i+j);
				} else if (size == I2C_SMBUS_WORD_DATA) {
					res = i2c_smbus_read_word_data(file,
								       i+j);
					if (res < 0) {
						block[i+j] = res;
						block[i+j+1] = res;
					} else {
						block[i+j] = res & 0xff;
						block[i+j+1] = res >> 8;
					}
				} else if (size == I2C_SMBUS_BYTE) {
					block[i+j] = res =
					  i2c_smbus_read_byte(file);
				} else
					res = block[i+j];

				if (size == I2C_SMBUS_BLOCK_DATA
				 && i+j >= s_length) {
					printf("   ");
				} else if (res < 0) {
					printf("XX ");
					if (size == I2C_SMBUS_WORD_DATA)
						printf("XX ");
				} else {
					printf("%02x ", block[i+j]);
					if (size == I2C_SMBUS_WORD_DATA)
						printf("%02x ", block[i+j+1]);
				}
				if (size == I2C_SMBUS_WORD_DATA)
					j++;
			}
			printf("   ");

			for (j = 0; j < 16; j++) {
				if (size == I2C_SMBUS_BLOCK_DATA
				 && i+j >= s_length)
					break;
				/* Skip unwanted registers */
				if (i+j < first || i+j > last) {
					printf(" ");
					continue;
				}

				res = block[i+j];
				if (res < 0)
					printf("X");
				else
				if ((res & 0xff) == 0x00
				 || (res & 0xff) == 0xff)
					printf(".");
				else
				if ((res & 0xff) < 32
				 || (res & 0xff) >= 127)
					printf("?");
				else
					printf("%c", res & 0xff);
			}
			printf("\n");
		}
Exemplo n.º 13
0
Arquivo: i2cget.c Projeto: muojie/my_c
int main(int argc, char *argv[])
{
	char *end;
	int res, i2cbus, address, file;
	int size = I2C_SMBUS_BYTE_DATA;
	int daddress;
	char filename[20];
	int pec = 0;
	int flags = 0;
	int force = 0, yes = 0, version = 0;

	/* handle (optional) flags first */
	while (1+flags < argc && argv[1+flags][0] == '-') {
		switch (argv[1+flags][1]) {
		case 'V': version = 1; break;
		case 'f': force = 1; break;
		case 'y': yes = 1; break;
		default:
			fprintf(stderr, "Warning: Unsupported flag "
				"\"-%c\"!\n", argv[1+flags][1]);
			help();
			exit(1);
		}
		flags++;
	}

	if (version) {
		fprintf(stderr, "i2cget version %s\n", VERSION);
		exit(0);
	}

	if (argc - flags < 3)
		help();

	i2cbus = strtol(argv[flags+1], &end, 0);
	if (*end || i2cbus < 0 || i2cbus > 0x3f) {
		fprintf(stderr, "Error: I2CBUS argument invalid!\n");
		help();
	}

	address = strtol(argv[flags+2], &end, 0);
	if (*end || address < 3 || address > 0x77) {
		fprintf(stderr, "Error: Chip address invalid!\n");
		help();
	}

	if (!(flags+3 < argc)) {
		size = I2C_SMBUS_BYTE;
		daddress = -1;
	} else {
		daddress = strtol(argv[flags+3], &end, 0);
		if (*end || daddress < 0 || daddress > 0xff) {
			fprintf(stderr, "Error: Data address invalid!\n");
			help();
		}
	}

	if (flags+4 < argc) {
		switch (argv[flags+4][0]) {
		case 'b': size = I2C_SMBUS_BYTE_DATA; break;
		case 'w': size = I2C_SMBUS_WORD_DATA; break;
		case 'c': size = I2C_SMBUS_BYTE; break;
		default:
			fprintf(stderr, "Error: Invalid mode!\n");
			help();
		}
		pec = argv[flags+4][1] == 'p';
	}

	file = open_i2c_dev(i2cbus, filename, 0);
	if (file < 0
	 || check_funcs(file, i2cbus, size, daddress, pec)
	 || set_slave_addr(file, address, force))
		exit(1);

	if (!yes && !confirm(filename, address, size, daddress, pec))
	 	exit(0);

	if (pec && ioctl(file, I2C_PEC, 1) < 0) {
		fprintf(stderr, "Error: Could not set PEC: %s\n",
		        strerror(errno));
		exit(1);
	}

	switch (size) {
	case I2C_SMBUS_BYTE:
		if (daddress >= 0) {
			res = i2c_smbus_write_byte(file, daddress);
			if (res < 0)
				fprintf(stderr, "Warning - write failed\n");
		}
		res = i2c_smbus_read_byte(file);
		break;
	case I2C_SMBUS_WORD_DATA:
		res = i2c_smbus_read_word_data(file, daddress);
		break;
	default: /* I2C_SMBUS_BYTE_DATA */
		res = i2c_smbus_read_byte_data(file, daddress);
	}
	close(file);

	if (res < 0) {
		fprintf(stderr, "Error: Read failed\n");
		exit(2);
	}

	printf("0x%0*x\n", size == I2C_SMBUS_WORD_DATA ? 4 : 2, res);

	exit(0);
}
Exemplo n.º 14
0
int main(int argc, char *argv[])
{
	char *end;
	int i, j, res, i2cbus, address, size, file;
	int bank = 0, bankreg = 0x4E, old_bank = 0;
	char filename[20];
	unsigned long funcs;
	int block[256], s_length = 0;
	int pec = 0, even = 0;
	int flags = 0;
	int force = 0, yes = 0, version = 0;

	/* handle (optional) flags first */
	while (1+flags < argc && argv[1+flags][0] == '-') {
		switch (argv[1+flags][1]) {
		case 'V': version = 1; break;
		case 'f': force = 1; break;
		case 'y': yes = 1; break;
		default:
			fprintf(stderr, "Warning: Unsupported flag "
				"\"-%c\"!\n", argv[1+flags][1]);
			help();
			exit(1);
		}
		flags++;
	}

	if (version) {
		fprintf(stderr, "i2cdump version %s\n", VERSION);
		exit(0);
	}

	if (argc < flags + 2) {
		fprintf(stderr, "Error: No i2c-bus specified!\n");
		help();
		exit(1);
	}
	i2cbus = strtol(argv[flags+1], &end, 0);
	if (*end) {
		fprintf(stderr, "Error: First argument not a number!\n");
		help();
		exit(1);
	}
	if (i2cbus < 0 || i2cbus > 0xff) {
		fprintf(stderr, "Error: I2CBUS argument out of range!\n");
		help();
		exit(1);
	}

	if (argc < flags + 3) {
		fprintf(stderr, "Error: No address specified!\n");
		help();
		exit(1);
	}
	address = strtol(argv[flags+2], &end, 0);
	if (*end) {
		fprintf(stderr, "Error: Second argument not a number!\n");
		help();
		exit(1);
	}
	if (address < 0 || address > 0x7f) {
		fprintf(stderr, "Error: Address out of range!\n");
		help();
		exit(1);
	}

	if (argc < flags + 4) {
		fprintf(stderr, "No size specified (using byte-data access)\n");
		size = I2C_SMBUS_BYTE_DATA;
	} else if (!strncmp(argv[flags+3], "b", 1)) {
		size = I2C_SMBUS_BYTE_DATA;
		pec = argv[flags+3][1] == 'p';
	} else if (!strncmp(argv[flags+3], "w", 1)) {
		size = I2C_SMBUS_WORD_DATA;
		pec = argv[flags+3][1] == 'p';
	} else if (!strncmp(argv[flags+3], "W", 1)) {
		size = I2C_SMBUS_WORD_DATA;
		even = 1;
	} else if (!strncmp(argv[flags+3], "s", 1)) {
		size = I2C_SMBUS_BLOCK_DATA;
		pec = argv[flags+3][1] == 'p';
	} else if (!strncmp(argv[flags+3], "c", 1)) {
		size = I2C_SMBUS_BYTE;
		pec = argv[flags+3][1] == 'p';
	} else if (!strcmp(argv[flags+3], "i"))
		size = I2C_SMBUS_I2C_BLOCK_DATA;
	else {
		fprintf(stderr, "Error: Invalid mode!\n");
		help();
		exit(1);
	}

	if (argc > flags + 4) {
		bank = strtol(argv[flags+4], &end, 0);
		if (*end || size == I2C_SMBUS_I2C_BLOCK_DATA) {
			fprintf(stderr, "Error: Invalid bank number!\n");
			help();
			exit(1);
		}
		if ((size == I2C_SMBUS_BYTE_DATA || size == I2C_SMBUS_WORD_DATA)
		 && (bank < 0 || bank > 15)) {
			fprintf(stderr, "Error: bank out of range!\n");
			help();
			exit(1);
		}
		if (size == I2C_SMBUS_BLOCK_DATA
		 && (bank < 0 || bank > 0xff)) {
			fprintf(stderr, "Error: block command out of range!\n");
			help();
			exit(1);
		}

		if (argc > flags + 5) {
			bankreg = strtol(argv[flags+5], &end, 0);
			if (*end || size == I2C_SMBUS_BLOCK_DATA) {
				fprintf(stderr, "Error: Invalid bank register "
				        "number!\n");
				help();
				exit(1);
			}
			if (bankreg < 0 || bankreg > 0xff) {
				fprintf(stderr, "Error: bank out of range "
				        "(0-0xff)!\n");
				help();
				exit(1);
			}
		}
	}

	file = open_i2c_dev(i2cbus, filename, 0);
	if (file < 0) {
		exit(1);
	}

	/* check adapter functionality */
	if (ioctl(file, I2C_FUNCS, &funcs) < 0) {
		fprintf(stderr, "Error: Could not get the adapter "
		        "functionality matrix: %s\n", strerror(errno));
		exit(1);
	}

	switch(size) {
	case I2C_SMBUS_BYTE:
		if (!((funcs & I2C_FUNC_SMBUS_BYTE) == I2C_FUNC_SMBUS_BYTE)) {
			fprintf(stderr, "Error: Adapter for i2c bus %d does "
				"not have byte capability\n", i2cbus);
			exit(1);
		}
		break;

	case I2C_SMBUS_BYTE_DATA:
		if (!(funcs & I2C_FUNC_SMBUS_READ_BYTE_DATA)) {
			fprintf(stderr, "Error: Adapter for i2c bus %d does "
				"not have byte read capability\n", i2cbus);
			exit(1);
		}
		break;

	case I2C_SMBUS_WORD_DATA:
		if (!(funcs & I2C_FUNC_SMBUS_READ_WORD_DATA)) {
			fprintf(stderr, "Error: Adapter for i2c bus %d does "
				"not have word read capability\n", i2cbus);
			exit(1);
		}
		break;

	case I2C_SMBUS_BLOCK_DATA:
		if (!(funcs & I2C_FUNC_SMBUS_READ_BLOCK_DATA)) {
			fprintf(stderr, "Error: Adapter for i2c bus %d does "
				"not have smbus block read capability\n",
				i2cbus);
			exit(1);
		}
		break;

	case I2C_SMBUS_I2C_BLOCK_DATA:
		if (!(funcs & I2C_FUNC_SMBUS_READ_I2C_BLOCK)) {
			fprintf(stderr, "Error: Adapter for i2c bus %d does "
			        "not have i2c block read capability\n",
			        i2cbus);
			exit(1);
		}
		break;
	}

	if (set_slave_addr(file, address, force) < 0)
		exit(1);

	if (pec) {
		if (ioctl(file, I2C_PEC, 1) < 0) {
			fprintf(stderr, "Error: Could not set PEC: %s\n",
			        strerror(errno));
			exit(1);
		}
		if (!(funcs & (I2C_FUNC_SMBUS_PEC | I2C_FUNC_I2C))) {
			fprintf(stderr, "Warning: Adapter for i2c bus %d does "
			        "not seem to actually support PEC\n", i2cbus);
		}
	}

	if (!yes) {
		fprintf(stderr, "WARNING! This program can confuse your I2C "
		        "bus, cause data loss and worse!\n");

		fprintf(stderr, "I will probe file %s, address 0x%x, mode "
		        "%s\n", filename, address,
		        size == I2C_SMBUS_BLOCK_DATA ? "smbus block" :
		        size == I2C_SMBUS_I2C_BLOCK_DATA ? "i2c block" :
		        size == I2C_SMBUS_BYTE ? "byte consecutive read" :
		        size == I2C_SMBUS_BYTE_DATA ? "byte" : "word");
		if (pec)
			fprintf(stderr, "PEC checking enabled.\n");
		if (even)
			fprintf(stderr, "Only probing even register "
			        "addresses.\n");
		if (bank) {
			if (size == I2C_SMBUS_BLOCK_DATA)
				fprintf(stderr, "Using command 0x%02x.\n",
				        bank);
			else
				fprintf(stderr, "Probing bank %d using bank "
				        "register 0x%02x.\n", bank, bankreg);
		}

		fprintf(stderr, "Continue? [Y/n] ");
		fflush(stderr);
		if (!user_ack(1)) {
			fprintf(stderr, "Aborting on user request.\n");
			exit(0);
		}
	}

	/* See Winbond w83781d data sheet for bank details */
	if (bank && size != I2C_SMBUS_BLOCK_DATA) {
		res = i2c_smbus_read_byte_data(file, bankreg);
		if (res >= 0) {
			old_bank = res;
			res = i2c_smbus_write_byte_data(file, bankreg,
				bank | (old_bank & 0xf0));
		}
		if (res < 0) {
			fprintf(stderr, "Error: Bank switching failed\n");
			exit(1);
		}
	}

	/* handle all but word data */
	if (size != I2C_SMBUS_WORD_DATA || even) {
		/* do the block transaction */
		if (size == I2C_SMBUS_BLOCK_DATA
		 || size == I2C_SMBUS_I2C_BLOCK_DATA) {
			unsigned char cblock[288];

			if (size == I2C_SMBUS_BLOCK_DATA) {
				res = i2c_smbus_read_block_data(file, bank,
				      cblock);
				/* Remember returned block length for a nicer
				   display later */
				s_length = res;
			} else {
				for (res = 0; res < 256; res += i) {
					i = i2c_smbus_read_i2c_block_data(file,
						res, 32, cblock + res);
					if (i <= 0)
						break;
				}
			}
			if (res <= 0) {
				fprintf(stderr, "Error: Block read failed, "
				        "return code %d\n", res);
				exit(1);
			}
			if (res >= 256)
				res = 256;
			for (i = 0; i < res; i++)
				block[i] = cblock[i];
			if (size != I2C_SMBUS_BLOCK_DATA)
				for (i = res; i < 256; i++)
					block[i] = -1;
		}

		if (size == I2C_SMBUS_BYTE) {
			res = i2c_smbus_write_byte(file, 0);
			if(res != 0) {
				fprintf(stderr, "Error: Write start address "
				        "failed, return code %d\n", res);
				exit(1);
			}
		}

		printf("     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f"
		       "    0123456789abcdef\n");
		for (i = 0; i < 256; i+=16) {
			if (size == I2C_SMBUS_BLOCK_DATA && i >= s_length)
				break;
			printf("%02x: ", i);
			for (j = 0; j < 16; j++) {
				fflush(stdout);
				if (size == I2C_SMBUS_BYTE_DATA) {
					block[i+j] = res =
					  i2c_smbus_read_byte_data(file, i+j);
				} else if (size == I2C_SMBUS_WORD_DATA) {
					res = i2c_smbus_read_word_data(file,
					                               i+j);
					if (res < 0) {
						block[i+j] = res;
						block[i+j+1] = res;
					} else {
						block[i+j] = res & 0xff;
						block[i+j+1] = res >> 8;
					}
				} else if (size == I2C_SMBUS_BYTE) {
					block[i+j] = res =
					  i2c_smbus_read_byte(file);
				} else
					res = block[i+j];

				if (size == I2C_SMBUS_BLOCK_DATA
				 && i+j >= s_length) {
					printf("   ");
				} else if (res < 0) {
					printf("XX ");
					if (size == I2C_SMBUS_WORD_DATA)
						printf("XX ");
				} else {
					printf("%02x ", block[i+j]);
					if (size == I2C_SMBUS_WORD_DATA)
						printf("%02x ", block[i+j+1]);
				}
				if (size == I2C_SMBUS_WORD_DATA)
					j++;
			}
			printf("   ");

			for (j = 0; j < 16; j++) {
				if (size == I2C_SMBUS_BLOCK_DATA
				 && i+j >= s_length)
					break;

				res = block[i+j];
				if (res < 0)
					printf("X");
				else
				if ((res & 0xff) == 0x00
				 || (res & 0xff) == 0xff)
					printf(".");
				else
				if ((res & 0xff) < 32
				 || (res & 0xff) >= 127)
					printf("?");
				else
					printf("%c", res & 0xff);
			}
			printf("\n");
		}
int main(int argc, char** argv, char**envp)
{
	// Initialize bitmap to be displayed
	__u16 board[]=
		{0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000};

        struct pollfd fdset[5];
        int nfds = 5;
        int gpio_fd1,gpio_fd2,gpio_fd3,gpio_fd4, timeout, rc;
        char buf[MAX_BUF];
        unsigned int gpio_in1,gpio_in2,gpio_in3,gpio_in4;
        unsigned int gpio_out1,gpio_out2,gpio_out3,gpio_out4;
	int x,y,wait,size;

	int res, i2cbus, address, file;
        char filename[20];
        int force = 0;
        int demo = 0;
	size = 8;

	// Find the i2c Bus
	i2cbus = lookup_i2c_bus("1");
        printf("i2cbus = %d\n", i2cbus);
        if (i2cbus < 0)
                help();
	
	// Getthe address of the led array
        address = parse_i2c_address("0x70");
        printf("address = 0x%2x\n", address);
        if (address < 0)
                help();

	// Get the file to operate the i2c bus
        file = open_i2c_dev(i2cbus, filename, sizeof(filename), 0);
        if (file < 0
         || check_funcs(file)
         || set_slave_addr(file, address, force))
                exit(1);

        // Check the return value on these if there is trouble
        i2c_smbus_write_byte(file, 0x21); // Start oscillator (p10)
        i2c_smbus_write_byte(file, 0x81); // Disp on, blink off (p11)
        i2c_smbus_write_byte(file, 0xe7); // Full brightness (page 15)


	wait = 0;
	x = 0;
	y = -1;

        int len;
	
	// Set GPIO pin numbers
        gpio_in1 = 30;
        gpio_in2 = 31;
        gpio_in3 = 48;
        gpio_in4 = 60;

	// Open each of the GPIO ports
        gpio_export(gpio_in1);
        gpio_export(gpio_in2);
        gpio_export(gpio_in3);
        gpio_export(gpio_in4);

	// Make all the GPIO ports inputs
        gpio_set_dir(gpio_in1, "in");
        gpio_set_dir(gpio_in2, "in");
        gpio_set_dir(gpio_in3, "in");
        gpio_set_dir(gpio_in4, "in");

        // Only trigger on the rising edge of the button
	gpio_set_edge(gpio_in1, "rising");
        gpio_set_edge(gpio_in2, "rising");
        gpio_set_edge(gpio_in3, "rising");
        gpio_set_edge(gpio_in4, "rising");

	// Open the button
        gpio_fd1 = gpio_fd_open(gpio_in1, O_RDONLY);
        gpio_fd2 = gpio_fd_open(gpio_in2, O_RDONLY);
        gpio_fd3 = gpio_fd_open(gpio_in3, O_RDONLY);
        gpio_fd4 = gpio_fd_open(gpio_in4, O_RDONLY);

        timeout = POLL_TIMEOUT;
		

	// Running Loop
        while(keepgoing){
                memset((void*)fdset, 0, sizeof(fdset));

		// Setup interrups for each button
                fdset[1].fd = gpio_fd1;
                fdset[1].events = POLLPRI;

                fdset[2].fd = gpio_fd2;
                fdset[2].events = POLLPRI;

                fdset[3].fd = gpio_fd3;
                fdset[3].events = POLLPRI;

                fdset[4].fd = gpio_fd4;
                fdset[4].events = POLLPRI;
		write_block(file, board);
		// Poll the buttons
                rc = poll(fdset, nfds, timeout);

		// If top button is pressed
                if (fdset[1].revents){
                        lseek(fdset[1].fd, 0, SEEK_SET);
                        len = read(fdset[1].fd, buf, MAX_BUF);

			// Check to see if boundry is hit
			if(y > 0 && wait > 2){	
				y = y - 1;
	            	}
				wait++;
                      
                }
		// If left button is pressed
     	        if (fdset[2].revents){
		        lseek(fdset[2].fd, 0, SEEK_SET);
                        len = read(fdset[2].fd, buf, MAX_BUF);

			// Check to see if boundry is hit
			if(x > 0 && wait > 2){
				x = x - 1;
			}else
				wait++;
			

                }
		// If right button pressed
                if (fdset[3].revents){
                        lseek(fdset[3].fd, 0, SEEK_SET);
                        len = read(fdset[3].fd, buf, MAX_BUF);
			// Check to see if boundry is hit
			if(x < size && wait > 2){
				x = x + 1;
			}else
				wait++;
			

                }
		// If bottom button is pressed
                if (fdset[4].revents){
                        lseek(fdset[4].fd, 0, SEEK_SET);
                        len = read(fdset[4].fd, buf, MAX_BUF);
	
			// Check to see if boundry is hit
			if(y < size && wait > 2){
				y = y + 1;
			}else
				wait++;
                }

		//y Corresponds to row in the bit map. Then x is how far in the bit has to be turned on, so I used a shift
		board[y] = (1 << x) | board[y];
                fflush(stdout);

        }
	
	// Close GPIO ports
        gpio_fd_close(gpio_fd1);
        gpio_fd_close(gpio_fd2);
        gpio_fd_close(gpio_fd3);
        gpio_fd_close(gpio_fd4);

	// Close ncursers

        return 0;
}