Commit ce461dd7 authored by Zhaozhong Liu's avatar Zhaozhong Liu
Browse files

lab 10 complete

parent 9a332d3d
#
# CSCI 315 Operating Systems Design
# Author: L. Felipe Perrone
# Date: 2011-04-21
# Copyright (c) 2011 Bucknell University
#
# Permission is hereby granted, free of charge, to any individual or
# institution obtaining a copy of this software and associated
# documentation files (the "Software"), to use, copy, modify, and
# distribute without restriction, provided that this copyright and
# permission notice is maintained, intact, in all copies and supporting
# documentation.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
# IN NO EVENT SHALL BUCKNELL UNIVERSITY BE LIABLE FOR ANY CLAIM, DAMAGES
# OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
# OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE
# OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
# compiler
CC = gcc
CFLAGS = -g -Wall
LIB = -lpthread
EXE = file_stat read_dir fdump traverse sender receiver
all: $(EXE)
file_stat: file_stat.o
$(CC) $(CFLAGS) -o file_stat file_stat.o
file_stat.o: file_stat.c
$(CC) -c $(CFLAGS) file_stat.c
read_dir: read_dir.o
$(CC) -o read_dir read_dir.o
read_dir.o: read_dir.c
$(CC) -c $(CFLAGS) read_dir.c
traverse: traverse.o
$(CC) $(CFLAGS) -o traverse traverse.o
traverse.o: traverse.c
$(CC) -c $(CFLAGS) traverse.c
receiver: receiver.o
$(CC) $(CFLAGS) -o receiver receiver.o $(LIB)
receiver.o: receiver.c
$(CC) -c $(CFLAGS) receiver.c
sender: sender.o
$(CC) $(CFLAGS) -o sender sender.o $(LIB)
sender.o: sender.c
$(CC) -c $(CFLAGS) sender.c
hexdump.o: hexdump.h hexdump.c
$(CC) $(CFLAGS) -c hexdump.c -o hexdump.o
fdump: fdump.c hexdump.o
$(CC) $(CFLAGS) hexdump.o fdump.c -o fdump
clean:
/bin/rm -f *~ *.o core $(EXE)
Lab 10
Prob 3
1: Here is the command to change only time of last status change:
chmod 777 file
2: Here is the command to change time of modification:
touch -m file
3: Here is the command to change time of access:
touch -a file
4: Knowing the maximum file length is helpful in the case when a file
is being copied to another file. Since, you may not want to exceed
the file length of the file you are copying to.
\ No newline at end of file
#include <stdio.h>
#include <stdlib.h>
#include "hexdump.h"
int main(int argc, char *argv[]) {
char *filename;
unsigned int offset;
unsigned int size;
FILE *fp;
if (argc != 4) {
printf("Usage: fdump [filename] [offset] [size]\n");
exit(-1);
}
filename = argv[1];
offset = atoi(argv[2]);
size = atoi(argv[3]);
char buffer[size];
// this will open the corresponding file
fp = fopen(filename, "r");
fseek(fp, (long) offset, SEEK_SET);
fread(buffer, (size_t) size, 1, fp);
hexdump((unsigned char *) buffer, size);
}
\ No newline at end of file
#include <limits.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <grp.h>
#include <fcntl.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/statvfs.h>
#include <pwd.h>
#include <time.h>
#include <unistd.h>
int main(int argc, char *argv[]) {
//to make and create the point
char *name;
struct tm time;
//the name of the str
char asctime_str[35];
//////////////////////////////////////////////////////////////////////
//////////////////////////////////////////////////////////////////////
unsigned int mode;
//////////////////////////////////////////////////////////////////////
// to make the umode for this problem
unsigned int umode;
unsigned int gmode;
unsigned int omode;
//to determine if human have the right to read write execute
char perm_bits_str[] = "---------";
unsigned int fd;
struct stat file_info;
struct statvfs fs_info;
//pass to fstat the pointer to an instance of stat struct
char resolved_path[PATH_MAX];
char* ret_path;
///////////////////////////////////////////
if (2 != argc) {
printf(" usage: %s [file_name]\n", argv[0]);
exit(-11);
}
// post-condition: argv[1] contains name of file to use
fd = open(argv[1], O_RDONLY);
if (-1 == fd) {
perror("Failed to open read only file - ");
exit(-1);
}
// use fstatvfs to learn details about the file system
if (fstatvfs(fd, &fs_info) == 0) {
printf("== FILE SYSTEM INFO ============================\n");
printf(" file system fstatvfs() call successful\n");
printf(" file system block size: %ld\n", fs_info.f_bsize); // Done
printf(" max. file name length: %ld\n", fs_info.f_namemax); // Done
} else {
printf("%s: File system fstatvfs call failed\n", argv[0]);
exit(-1);
}
///////////////////////////////////////////////////////////////
name = calloc(fs_info.f_namemax, 1);
if (NULL == name) {
perror("Problem in calloc - ");
exit(-1);
}
// copy file name into name variable using secure version of string copy
strncpy(name, argv[1], 500);
// use fstat to get information on specific file
if (fstat(fd, &file_info) == 0) {
printf("\n== FILE INFO ============================\n");
printf(" file fstat() call successful\n");
// mode comes from the lower 9 bits in file_info.st_mode
mode = file_info.st_mode & 0x1FF;
printf(" file protection bits = 0%o\n", mode);
// umode comes from the high 3 bits in mode
umode = mode >> 6 & 0x7; // Done
// gmode comes from the middle 3 bits in mode
gmode = mode >> 3 & 0x7; // Done
// omode comes from the low 3 bits in mode
omode = mode & 0x7; // Done
// once you have set umode, gmode, and omode, the code below
// will construct the right string for you and display it
// construct string with file protection information
if (umode & 0x4) perm_bits_str[0] = 'r';
if (umode & 0x2) perm_bits_str[1] = 'w';
if (umode & 0x1) perm_bits_str[2] = 'x';
if (gmode & 0x4) perm_bits_str[3] = 'r';
if (gmode & 0x2) perm_bits_str[4] = 'w';
if (gmode & 0x1) perm_bits_str[5] = 'x';
if (omode & 0x4) perm_bits_str[6] = 'r';
if (omode & 0x2) perm_bits_str[7] = 'w';
if (omode & 0x1) perm_bits_str[8] = 'x';
printf(" file protection string = %s\n", perm_bits_str);
printf(" file protection mode (u:g:o) = %o:%o:%o\n",
umode, gmode, omode);
struct passwd *user_info = getpwuid(file_info.st_uid);
struct group *group_info = getgrgid(file_info.st_gid);
printf(" owner user name = %s\n", user_info->pw_name); // Done: man getpwuid
printf(" owner group name = %s\n", group_info->gr_name); // Done: man getgrgid
if (S_ISREG(file_info.st_mode)) {
printf(" mode = regular file\n");
} else {
if (S_ISDIR(file_info.st_mode)) printf(" mode = directory\n");
else if (S_ISCHR(file_info.st_mode)) printf(" mode = character device\n");
else if (S_ISBLK(file_info.st_mode)) printf(" mode = block device\n");
else if (S_ISLNK(file_info.st_mode)) printf(" mode = symbolic link\n");
else if (S_ISSOCK(file_info.st_mode)) printf(" mode = socket\n");
else if (S_ISFIFO(file_info.st_mode)) printf(" mode = fifo\n");
else printf(" mode = unkown\n");
}
ret_path = realpath(name, resolved_path);
if (NULL != ret_path)
printf(" absolute path = %s\n", ret_path);
else {
perror(" couldn't resolve path");
exit(-1);
}
/////////////////////////////////////////////////////////
localtime_r(&(file_info.st_mtime), &time);
asctime_r(&time, asctime_str);
printf(" time of last modification: %s\n", asctime_str);
localtime_r(&(file_info.st_atime), &time);
asctime_r(&time, asctime_str);
printf(" time of last access: %s\n", asctime_str);
localtime_r(&(file_info.st_ctime), &time);
asctime_r(&time, asctime_str);
printf(" time of status change: %s\n", asctime_str);
fflush(stdout);
close(fd);
exit(0);
}
else
printf(" fstat call failed\n");
return 0;
}
#include <stdio.h>
/////////////////////////////////////////////,
char is_printable(unsigned char c) {
if ((c >= 0x20) && (c < 0x7F))
return c;
else
return '.';
}
/////////////////////////////////////////////,,
void hexdump(unsigned char* buffer, unsigned int length) {
int b=0, c=0;
int s, rem;
/////////////////////////////////////////////,,
printf("\n PAYLOAD HEXDUMP:\n");
while (b < length) {
printf("\n %07x:", b);
for (; (b%16<15) && (b<length); b++) {
if (0 == b % 2)
printf(" ");
printf("%02hhx", buffer[b]);
}
/////////////////////////////////////////////,
if (b < length)
printf("%02hhx ", buffer[b++]);
else { // print a number of spaces to align the remaining text
rem = b % 16;
for (s=0; s < 44 - ((rem*2) + (rem/2) + 1); s++)
printf(" ");
}
/////////////////////////////////////////////,
for (;(c%16<15) && (c<length); c++) {
printf("%c", is_printable(buffer[c]));
}
if (c<length)
printf("%c", is_printable(buffer[c++]));
}
}
#ifndef __HEXDUMP_H__
#define __HEXDUMP_H__
/////////////////////////////////////////////,
extern void hexdump(unsigned char* buffer, unsigned int length);
#endif /* __HEXDUMP_H__ */
Prelab 10
Problem 2:
2.1: On the right, I see the offsetted text of the code from the file hexdump.c
whereas on the left, I see 8 sets of hexadecimal values.
2.2: Similar to what I saw for hexdump.c, I see the offsetted content of the file
fdump (which is an executable) on the right. The left side is still a set of
hexadecimal values.
2.3: The reason why the right hand side content for 2.2 is not human-readable is
because the actual content of that file is not human-readable because it is
machine code. Since the program is displaying the ASCII representation of the
content of file we see giberish here. Whereas, in case of 2.1 the content of
file is human-readable C code which is why in 2.1 we see human-readable content.
2.4: Running file(1) command on the provided file paths I see the type of the file
for which I provided the path. For example in case of file "work" I see file
type as "PDF document" and the file's version.
The way file(1) works is by performing three sets of tests. The first is
filesystem test which makes a stat(2) system call and gets info about the
file as pointed by its path. The second test is the magic test which checks
for a "magic" number that some file types have stored. This can tell the system
about the file type as well. Last test is the language test which basically
checks which language the file is writeen in. [Source: manual file(1) and stat(2)]
\ No newline at end of file
#include "read_dir.h"
/////////////////////////////////////////////,
//protoype of the funcs
void process(char *name);
void enqueue(char *name, que_t *q);
void dequeue(que_t *q);
void peek_front(char *name,que_t q);
bool queue_empty(que_t q);
void initq(que_t *q);
//the main of the programm
int main(int argc,char *argv[]) {
if (2 != argc) {
printf(" usage: %s dirpath\n", argv[0]);
exit(-1);
}
else {
// pass in the starting directory
process(argv[1]);
}
return 0;
}
/////////////////////////////////////////////,
//go through all and try each
void process(char *root)
{
int numOfFiles = 0;
que_t nameq;
char dname[MAXLENGTH];
char cname[MAXLENGTH];
char prefix[MAXLENGTH];
struct dirent *dp;
DIR *dirp;
initq(&nameq);
enqueue(root,&nameq);
while (true != queue_empty(nameq)) {
peek_front(dname,nameq);
dequeue(&nameq);
dirp = opendir(dname);
if (dirp != NULL) { // it is a directory
printf("directory : %s\n",dname);
strncpy(prefix, dname, MAXLENGTH);
strncat(prefix,"/", MAXLENGTH);
for (dp = readdir(dirp); NULL != dp; dp = readdir(dirp)) {
if ((strcmp(dp->d_name,"..") != 0) &&
(strcmp(dp->d_name,".") != 0)) {
// prevent from infinite loop
strncpy(cname, prefix, MAXLENGTH);
// concatenate the prefix
strncat(cname, dp->d_name, MAXLENGTH);
enqueue(cname,&nameq);
}
}
closedir (dirp);
} else {
// test if it is a regular file and not a device or link -- TO-DO
// if this is a regular file, then process it -- TO-DO
printf(" processing file: %s\n", dname);
numOfFiles++;
}
}
printf(" a total of %d files were counted\n",numOfFiles);
}
/////////////////////////////////////////////,
void initq(que_t *q) {
q->head = q->tail = NULL;
}
bool queue_empty(que_t q) {
if (NULL == q.head) {
return true;
} else {
return false;
}
}
/////////////////////////////////////////////,
void enqueue(char *name, que_t *q) {
item_t *temp;
temp = (item_t *)malloc(sizeof(item_t));
strncpy(temp->name,name,MAXLENGTH);
temp->next = NULL;
if (true == queue_empty(*q)) {
q->head = temp;
q->tail = temp;
} else {
q->tail->next = temp;
q->tail = q->tail->next;
}
}
/////////////////////////////////////////////,
void dequeue(que_t *q) {
item_t *temp;
if (true == queue_empty(*q)) {
printf(" error in dequeue \n");
exit(-1);
} else {
temp = q->head;
q->head = q->head->next;
free(temp);
}
}
/////////////////////////////////////////////,
void peek_front(char *name, que_t q) {
if (true == queue_empty(q)) {
printf(" error in dequeue \n");
exit(-1);
} else {
strncpy(name, q.head->name, MAXLENGTH);
}
}
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
#include <dirent.h>
#include <fcntl.h>
#include <ctype.h>
#include <sys/time.h>
#include <sys/param.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <stdbool.h>
#define MAXLENGTH 255 // for file names
#define BYTE 8
struct item_type
{
char name[MAXLENGTH];
int count;
struct item_type *next;
};
struct que_type
{
struct item_type *head, *tail;
};
typedef struct que_type que_t;
typedef struct item_type item_t;
#include <stdio.h>
#include <fcntl.h>
#include <string.h>
#include <stdbool.h>
#include <semaphore.h>
#define MAXLENGTH 255
#define CHANNEL "channel.txt"
int main(int argc, char *argv[]) {
sem_t *rec, *msg;
char msg_str[MAXLENGTH];
FILE *fd;
fd = fopen(CHANNEL, "rb");
sem_unlink("rec"); sem_unlink("msg");
rec = sem_open("rec", O_CREAT, 0777, 1);
msg = sem_open("msg", O_CREAT, 0777, 0);
/////////////////////////////////////////////,
while(1) {
// wait for msg and receiver
sem_wait(msg); sem_wait(rec);
// print the new message
if (fgets(msg_str, sizeof(msg_str), fd) != NULL)
printf("receiver [msg arrival]: %s", msg_str);
// signal received
sem_post(rec);
} // inifinite loop
}
\ No newline at end of file
#include <stdio.h>
#include <fcntl.h>
#include <string.h>
#include <stdlib.h>
#include <semaphore.h>
#define MAXLENGTH 255
#define CHANNEL "channel.txt"
int main(int argc, char *argv[]) {
/////////////////////////////////////////////,
sem_t *rec, *msg;
/////////////////////////////////////////////,
char msg_str[MAXLENGTH];
/////////////////////////////////////////////,
FILE *fd;
/////////////////////////////////////////////,
if (argc != 2) {
printf("usage: ./sender \"message\"\n");
exit(-1);
}
fd = fopen(CHANNEL, "a");
strcpy(msg_str, argv[1]);
/////////////////////////////////////////////,
rec = sem_open("rec", O_CREAT, 0777, 1);
msg = sem_open("msg", O_CREAT, 0777, 0);
/////////////////////////////////////////////,
sem_wait(rec);
/////////////////////////////////////////////,
fprintf(fd, "%s\n", msg_str);
/////////////////////////////////////////////,
sem_post(msg);
/////////////////////////////////////////////,
sem_post(rec);
fclose(fd);
}
\ No newline at end of file
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment