OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [trunk/] [uclinux/] [uC-libc/] [misc/] [getcwd.c] - Blame information for rev 1767

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 199 simons
 
2
#include <errno.h>
3
#include <sys/stat.h>
4
#include <dirent.h>
5
#include <string.h>
6
/*
7
 * These functions find the absolute path to the current working directory.
8
 *
9
 * They don't use malloc or large amounts of stack space.
10
 */
11
 
12
static char * recurser();       /* Routine to go up tree */
13
static char * search_dir();     /* Routine to find the step back down */
14
static char * path_buf;
15
static int    path_size;
16
 
17
static dev_t root_dev;
18
static ino_t root_ino;
19
 
20
static struct stat st;
21
 
22
char *
23
getcwd(buf, size)
24
char * buf;
25
int size;
26
{
27
   path_buf = buf;
28
   path_size = size;
29
 
30
   if( size < 3 ) { errno = ERANGE; return 0; }
31
   strcpy(path_buf, ".");
32
 
33
   if( stat("/", &st) < 0 ) return 0;
34
 
35
   root_dev = st.st_dev;
36
   root_ino = st.st_ino;
37
 
38
   return recurser();
39
}
40
 
41
static char *
42
recurser()
43
{
44
   dev_t this_dev;
45
   ino_t this_ino;
46
   if( stat(path_buf, &st) < 0 ) return 0;
47
   this_dev = st.st_dev;
48
   this_ino = st.st_ino;
49
   if( this_dev == root_dev && this_ino == root_ino )
50
   {
51
      strcpy(path_buf, "/");
52
      return path_buf;
53
   }
54
   if( strlen(path_buf) + 4 > path_size ) { errno = ERANGE; return 0; }
55
   strcat(path_buf, "/..");
56
   if( recurser() == 0 ) return 0;
57
 
58
   return search_dir(this_dev, this_ino);
59
}
60
 
61
static char *
62
search_dir(this_dev, this_ino)
63
dev_t this_dev;
64
ino_t this_ino;
65
{
66
   DIR * dp;
67
   struct dirent * d;
68
   char * ptr;
69
   int slen;
70
   /* The test is for ELKS lib 0.0.9, this should be fixed in the real kernel*/
71
   int slow_search = (sizeof(ino_t) != sizeof(d->d_ino));
72
 
73
   if( stat(path_buf, &st) < 0 ) return 0;
74
   if( this_dev != st.st_dev ) slow_search = 1;
75
 
76
   slen = strlen(path_buf);
77
   ptr = path_buf + slen -1;
78
   if( *ptr != '/' )
79
   {
80
      if( slen + 2 > path_size ) { errno = ERANGE; return 0; }
81
      strcpy(++ptr, "/");
82
      slen++;
83
   }
84
   slen++;
85
 
86
   dp = opendir(path_buf);
87
   if( dp == 0 ) return 0;
88
 
89
   while( (d=readdir(dp)) != 0 )
90
   {
91
      if( slow_search || this_ino == d->d_ino )
92
      {
93
         if( slen + strlen(d->d_name) > path_size )
94
            { errno = ERANGE; return 0; }
95
         strcpy(ptr+1, d->d_name);
96
         if( stat(path_buf, &st) < 0 )
97
            continue;
98
         if( st.st_ino == this_ino && st.st_dev == this_dev )
99
         {
100
            closedir(dp);
101
            return path_buf;
102
         }
103
      }
104
   }
105
 
106
   closedir(dp);
107
   errno = ENOENT;
108
   return 0;
109
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.