Building GNU Smalltalk-2.3.5 with MinGW

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
9 messages Options
Reply | Threaded
Open this post in threaded view
|

Building GNU Smalltalk-2.3.5 with MinGW

Akeroyd, FA (Freddie)
Hi,

I've been playing with compiling GNU Smalltalk-2.3.5 on MinGW and had
some success. I have been able to build the code and "make check" passes
with only one failure (quit.st), but some issues remain with paths that
need further work and, probably, more knowledge of the internals of GNU
Smalltalk than I have. With the enclosed changes applied, remaking the
documentation will fail due to path issues and any paths supplied need
to be in c:/some/where format rather than c:\some\where. I haven't
extensively tested the program further than "make check" so other issues
may be present too, but I'm posting my changes in the hope that they
might be useful towards a full MinGW port.

The build sequence I used was:

* Run    ./configure --without-readline --without-gmp
* Edit the top Makefile and change  `cygpath -w gsticon.ico`  to just
gsticon.ico
* in the tests directory run     unix2dos -o *.ok
* Apply the enclosed changes to lib-src/poll.c, libgst/cint.c,
libgst/sysdep.c, kernel/Directory.st, kernel/File.st and
kernel/FileDescr.st
* type  make
* type  make  again (the first make fails when rebuilding the classes
doc)
* make check (maybe more than once if it tries to rebuild the doc again)

Freddie



## ---------------------- ##
## Detailed failed tests. ##
## ---------------------- ##

#                             -*- compilation -*-
22. testsuite.at:48: testing ...
./testsuite.at:48: cd $abs_srcdir && $GST -r quit.st 2>&1
--- expout      Thu Jun 14 13:21:23 2007
+++ /home/faa59/smalltalk-2.3.5/tests/testsuite.dir/at-stdout   Thu Jun
14 13:21
:23 2007
@@ -1,2 +0,0 @@
-^M
-Execution begins...^M
22. testsuite.at:48: 22. quit.st (testsuite.at:48): FAILED
(testsuite.at:48)


## ---------------------- ##
## Code changes           ##
## ---------------------- ##

--- ../smalltalk-2.3.5-orig/lib-src/poll.c Wed Jan  3 10:51:30 2007
+++ lib-src/poll.c Thu Jun 14 13:55:29 2007
@@ -19,14 +19,45 @@
    with this program; if not, write to the Free Software Foundation,
    Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
 
+
 #include "config.h"
 
 #include <sys/types.h>
 #include "poll.h"
 #include <errno.h>
+#include <stdio.h>
 #include <limits.h>
-#include <sys/socket.h>
-#include <sys/select.h>
+#include <windows.h>
+#include <winsock2.h>
+#include <io.h>
+
+#undef FD_ISSET
+#define FD_ISSET(fd, set) my_fd_isset(fd, set)  /* to avoid a WSA call
*/
+
+static int my_fd_isset(int fd, fd_set* set)
+{
+ int i;
+ if (set == NULL)
+ {
+    return 0;
+ }
+ for(i=0; i < set->fd_count; i++)
+ {
+ if (set->fd_array[i] == fd)
+ {
+ return 1;
+ }
+ }
+ return 0;
+}
+
+#define ESHUTDOWN WSAESHUTDOWN
+#define ENOTCONN WSAENOTCONN
+#define ECONNRESET WSAECONNRESET
+#define ECONNABORTED WSAECONNABORTED
+#define ENETRESET WSAENETRESET
+
+typedef int nfds_t;
 #include <unistd.h>
 
 #ifdef HAVE_SYS_IOCTL_H
@@ -55,6 +86,76 @@
 #define EOVERFLOW EINVAL
 #endif
 
+// n = maxfd + 1
+#define MAX_WIN_HANDLES 300
+static int win_select(int n, fd_set *rfds, fd_set *wfds, fd_set *efds,
struct timeval *ptv)
+{
+ HANDLE handle_array[MAX_WIN_HANDLES];
+        int handle_fd[MAX_WIN_HANDLES];
+ fd_set* handle_set[MAX_WIN_HANDLES];
+ int i;
+ DWORD ret, wait_timeout, nhandles = 0;
+ int nset, done;
+ done = 0;
+ nset = 0;
+ _flushall();
+ for(i=0; i<n; i++)
+ {
+ if ((efds != NULL) && FD_ISSET(i, efds))
+ {
+ FD_CLR(i, efds); /*
assume no exceptions */
+ }
+ if ((wfds != NULL) && FD_ISSET(i, wfds))
+ {
+ handle_array[nhandles] =
(HANDLE)_get_osfhandle(i);
+ handle_fd[nhandles] = i;
+ handle_set[nhandles] = wfds;
+ nhandles++;
+ FD_CLR(i, wfds); /* we
will set it later if there is output */
+ }
+ if ((rfds != NULL) && FD_ISSET(i, rfds))
+ {
+ handle_array[nhandles] =
(HANDLE)_get_osfhandle(i);
+ handle_fd[nhandles] = i;
+ handle_set[nhandles] = rfds;
+ nhandles++;
+ FD_CLR(i, rfds); /* we
will set it later if there is input */
+ }
+ }
+/* do a quick poll - WaitForMultipleObjects only tells us if 1 handle
+ is ready and there may be more */
+ for(i=0; i<nhandles; i++)
+ {
+    ret = WaitForSingleObject(handle_array[i], 0);
+    if (ret == WAIT_OBJECT_0)
+    {
+ FD_SET(handle_fd[i], handle_set[i]);
+ nset++;
+    }
+ }
+ if ((nset == 0) && (nhandles > 0)) // nothing set, so
wait full time
+ {
+    if (ptv == NULL)
+    {
+ wait_timeout = INFINITE;
+    }
+    else
+    {
+ wait_timeout = ptv->tv_sec * 1000 + ptv->tv_usec
/ 1000;
+    }
+/* Need to use MsgWaitForMultipleObjects and maybe pump messages if a
GUI application? */
+
+ ret = WaitForMultipleObjectsEx(nhandles,
handle_array, FALSE, wait_timeout, FALSE);
+ i = ret - WAIT_OBJECT_0;
+ if (i >= 0 && i < nhandles)
+ {
+ FD_SET(handle_fd[i], handle_set[i]);
+ nset++;
+ }
+ }
+ return nset;
+}
+
 int
 poll (pfd, nfd, timeout)
      struct pollfd *pfd;
@@ -142,8 +243,9 @@
     }
 
   /* examine fd sets */
-  rc = select (maxfd + 1, &rfds, &wfds, &efds, ptv);
-  if (rc < 0)
+   rc = win_select (maxfd + 1, &rfds, &wfds, &efds, ptv);
+    
+ if (rc < 0)
     return rc;
 
   /* establish results */
@@ -158,6 +260,7 @@
   {
     int r;
     
+    char data[64];
 #if defined __MACH__ && defined __APPLE__
     /* There is a bug in Mac OS X that causes it to ignore
MSG_PEEK
        for some kinds of descriptors.  Detect if this descriptor
is a
@@ -167,9 +270,9 @@
     if (r == 0 || errno == ENOTSOCK)
       ioctl(pfd[i].fd, FIONREAD, &r);
 #else
-    char data[64];
-    r = recv (pfd[i].fd, data, sizeof (data), MSG_PEEK);
+//    r = recv (pfd[i].fd, data, sizeof (data), MSG_PEEK);
 #endif
+    r = 1;
     if (r == 0)
       happened |= POLLHUP;
     
--- ../smalltalk-2.3.5-orig/libgst/cint.c Thu Dec  7 08:09:12 2006
+++ libgst/cint.c Thu Jun 14 12:19:44 2007
@@ -341,7 +341,8 @@
   times[0].tv_sec = new_atime + 86400 * 10957;
   times[1].tv_sec = new_mtime + 86400 * 10957;
   times[0].tv_usec = times[1].tv_usec = 0;
-  result = utimes (name, times);
+  result = 0;
+  printf("utimes called\n"); /* needs fixing */
   if (!result)
     errno = 0;
   return (result);
--- ../smalltalk-2.3.5-orig/libgst/sysdep.c Mon May  7 14:12:04 2007
+++ libgst/sysdep.c Thu Jun 14 12:18:17 2007
@@ -710,7 +710,7 @@
   char *cwd;
   char *ret;
   unsigned path_max;
-  int save_errno;
+  int i, save_errno;
 
   path_max = (unsigned) PATH_MAX;
   path_max += 2; /* The getcwd docs say to do this.  */
@@ -721,6 +721,11 @@
   do
     {
       ret = getcwd (cwd, path_max);
+      for(i=0; i<strlen(cwd); i++)
+      {
+        if (cwd[i] == '\\')
+          cwd[i] = '/';
+      }
       if (ret)
  return (cwd);
 
--- ../smalltalk-2.3.5-orig/kernel/Directory.st Sun Feb  5 18:41:26 2006
+++ kernel/Directory.st Thu Jun 14 12:17:52 2007
@@ -108,6 +108,10 @@
     directory isEmpty ifTrue: [ ^fileName ].
     (fileName at: 1) = self pathSeparator
  ifTrue: [ ^fileName ].
+    "Check to see if building up a windows absolute path from scratch
i.e. appending X: to /"
+    ((directory = '/') and: [ (fileName size = 2) and: [ ((fileName at:
2) = $:) ]]) ifTrue: [ ^fileName ].
+    "Check for a complete absolute windows path of form X:/"
+    ((fileName size >= 3) and: [ ((fileName at: 2) = $:) and: [
((fileName at: 3) = $/) ]]) ifTrue: [ ^fileName ].
     (self pathSeparator = $\ and: [ fileName size >= 2 and: [
  (fileName at: 2) = $: ]]) ifTrue: [ ^fileName ].
     ^(directory at: directory size) = self pathSeparator
--- ../smalltalk-2.3.5-orig/kernel/File.st Sun Feb  5 18:41:26 2006
+++ kernel/File.st Thu Jun 14 12:17:00 2007
@@ -132,9 +132,19 @@
     "Answer the full path to a file called `aString', resolving the `.'
and
      `..' directory entries, and answer the result.  `/..' is the same
as '/'."
 
-    | path substrings |
+    | path substrings respath isAbsolute |
+    isAbsolute _ false.
+    "Windows paths starting X:/ are absolute"
+    (aString size >= 3) ifTrue: [
+ ( ((aString at: 2) = $:) & ((aString at: 3) = $/) ) ifTrue: [
+    isAbsolute _ true
+ ]
+    ].
+    ((aString at: 1) = Directory pathSeparator) ifTrue: [
+        isAbsolute _ true.
+    ].
     path := OrderedCollection new.
-    (aString at: 1) = Directory pathSeparator ifFalse: [
+    isAbsolute ifFalse: [
  path addAll: (Directory working substrings: Directory
pathSeparator).
     ].
     substrings := aString substrings: Directory pathSeparator.
@@ -148,9 +158,16 @@
  ]
     ].
 
-    ^path inject: '/' into: [ :old :each |
+    respath _ path inject: '/' into: [ :old :each |
  Directory append: each to: old
-    ]
+    ].
+    "remove initial / from /C:/"
+    (respath size >= 4) ifTrue: [
+ ( ((respath at: 1) = $/) & ((respath at: 3) = $:) & ((respath
at: 4) = $/) ) ifTrue: [
+    respath _ respath copyFrom: 2
+ ]
+    ].
+    ^respath
 ! !
 
 
--- ../smalltalk-2.3.5-orig/kernel/FileDescr.st Fri May 18 12:35:09 2007
+++ kernel/FileDescr.st Thu Jun 14 12:16:21 2007
@@ -103,7 +103,8 @@
      finished with it anyway, using #close. To keep a file open even
when
      no references exist anymore, send it #removeToBeFinalized"
 
-    ((fileName indexOfSubCollection: ':/') > 0 and: [
+"look for :// rather than :/ to avoid matching C:/some/where on
windows"
+    ((fileName indexOfSubCollection: '://') > 0 and: [
         fileMode = FileStream read ]) ifTrue: [
            ^NetClients.URIResolver openStreamOn: fileName ].



_______________________________________________
help-smalltalk mailing list
[hidden email]
http://lists.gnu.org/mailman/listinfo/help-smalltalk
Reply | Threaded
Open this post in threaded view
|

Re: Building GNU Smalltalk-2.3.5 with MinGW

Paolo Bonzini
Akeroyd, FA (Freddie) wrote:
 > Hi,
 >
 > I've been playing with compiling GNU Smalltalk-2.3.5 on MinGW and had
 > some success.

Great!

 > With the enclosed changes applied, remaking the
 > documentation will fail due to path issues and any paths supplied need
 > to be in c:/some/where format rather than c:\some\where.

The attached patch, on top of 2.3.5, is my take on this.  It fixes all
path issues, so the only things left should be:

1) modifying _gst_set_file_access_times to use the appropriate Windows
API function

2) figuring out what to do with poll

3) figuring out why tests are failing without unix2dos.  One possibility
could be the second patch I attach, please tell me if it works.

Please send future patches relative to this one (I suggest that you
create your own CVS/svn/Arch/git repository).  Thanks!

Paolo


2007-06-15  Freddie Akeroyd  <[hidden email]>
            Paolo Bonzini  <[hidden email]>

        * kernel/Character.st: Add #isPathSeparator.
        * kernel/Directory.st: Use it; add special cases for Win32 systems.
        * kernel/File.st: Use it; add special cases for Win32 systems.
        * kernel/FileDescr.st: Look for :// instead of :/ to distinguish URIs.

        * libgst/cint.c: Remove my_utime.
        * libgst/sysdep.c: Move it here as _gst_set_file_access_times.
        * libgst/sysdep.h: Declare it.
        * libgst/dict.c: Add CSymbols.PathSeparator.


--- orig/Makefile.am
+++ mod/Makefile.am
@@ -107,7 +107,7 @@ DISTCLEANFILES += config.h
 
 # These two lines add a beatiful icon to the Win32 executable
 gsticon.o: gsticon.ico
- echo ProgramIcon ICON `cygpath -w gsticon.ico` | windres -o gsticon.o
+ echo ProgramIcon ICON `$(CYGPATH_W) gsticon.ico` | windres -o gsticon.o
 
 gst.im: $(bin_PROGRAMS) $(srcdir)/kernel/stamp-classes
  SMALLTALK_KERNEL="`cd $(srcdir)/kernel; pwd`" \


--- orig/configure.ac
+++ mod/configure.ac
@@ -215,7 +215,7 @@ AC_REPLACE_FUNCS(putenv strdup strerror
  getdtablesize strstr ftruncate floorl ceill sqrtl frexpl ldexpl asinl \
  acosl atanl logl expl tanl sinl cosl truncl lrintl strsep strpbrk)
 AC_CHECK_FUNCS_ONCE(gethostname memcpy memmove sighold uname sbrk usleep lstat \
- grantpt popen getrusage gettimeofday getcwd fork strchr \
+ grantpt popen getrusage gettimeofday getcwd fork strchr utimes \
  sigsetmask alarm select mprotect madvise nl_langinfo waitpid \
  setsid spawnl nanosleep pread pwrite)
 


--- orig/kernel/Character.st
+++ mod/kernel/Character.st
@@ -258,6 +258,12 @@ isPunctuation
     ^(Table at: 1 + codePoint ifAbsent: [ 0 ]) = 4
 !
 
+isPathSeparator
+    "Returns true if self is a path separator ($/ or $\ under Windows,
+     $/ only under Unix systems including Mac OS X).
+    ^self == $/ or: [ self == Directory pathSeparator ]
+!
+
 isVowel
     "Returns true if self is a, e, i, o, or u; case insensitive"
     | char |


--- orig/kernel/Directory.st
+++ mod/kernel/Directory.st
@@ -106,26 +106,33 @@ append: fileName to: directory
     "Answer the name of a file named `fileName' which resides in a directory
      named `directory'."
     directory isEmpty ifTrue: [ ^fileName ].
-    (fileName at: 1) = self pathSeparator
- ifTrue: [ ^fileName ].
-    (self pathSeparator = $\ and: [ fileName size >= 2 and: [
- (fileName at: 2) = $: ]]) ifTrue: [ ^fileName ].
-    ^(directory at: directory size) = self pathSeparator
+    self pathSeparator == $\
+ ifFalse: [
+    (fileName at: 1) isPathSeparator ifTrue: [ ^fileName ] ]
+ ifTrue: [
+    (fileName at: 1) isPathSeparator ifTrue: [
+ ^(directory size >= 2 and: [ (directory at: 2) = $: ])
+    ifTrue: [ '%1:%2' bindWith: directory first with: fileName ]
+    ifFalse: [ fileName ] ].
+            (fileName size >= 2 and: [ (fileName at: 2) = $: ])
+ ifTrue: [ ^fileName ] ].
+
+    ^(directory at: directory size) isPathSeparator
  ifTrue: [ directory, fileName ]
  ifFalse: [ '%1%2%3'
     bindWith: directory
-    with: self pathSeparatorString
+    with: self pathSeparator
     with: fileName ]
 !
 
 pathSeparator
     "Answer (as a Character) the character used to separate directory names"
-    ^$/
+    ^CSymbols.PathSeparator
 !
 
 pathSeparatorString
     "Answer (in a String) the character used to separate directory names"
-    ^'/'
+    ^String with: self pathSeparator
 ! !
 
 


--- orig/kernel/File.st
+++ mod/kernel/File.st
@@ -132,9 +132,18 @@ fullNameFor: aString
     "Answer the full path to a file called `aString', resolving the `.' and
      `..' directory entries, and answer the result.  `/..' is the same as '/'."
 
-    | path substrings |
+    | path substrings result isAbsolute isWindows |
+
+    isAbsolute := (aString at: 1) isPathSeparator.
+    isWindows := Directory pathSeparator == $\.
+    "Windows paths starting X:/ are absolute"
+    (isWindows and: [
+        aString size >= 3 and: [
+ (aString at: 2) = $: and: [
+ (aString at: 3) isPathSeparator ]]]) ifTrue: [ isAbsolute := true ].
+
     path := OrderedCollection new.
-    (aString at: 1) = Directory pathSeparator ifFalse: [
+    isAbsolute ifFalse: [
  path addAll: (Directory working substrings: Directory pathSeparator).
     ].
     substrings := aString substrings: Directory pathSeparator.
@@ -148,9 +157,18 @@ fullNameFor: aString
  ]
     ].
 
-    ^path inject: '/' into: [ :old :each |
- Directory append: each to: old
-    ]
+    result := path inject: Directory pathSeparatorString into: [ :old :each |
+ Directory append: each to: old
+    ].
+
+    "Remove initial / from /C:/"
+    ^(isWindows and: [
+ result size >= 4 and: [
+ (result at: 1) isPathSeparator and: [
+ (result at: 3) = $: and: [
+ (result at: 4) isPathSeparator ]]]])
+    ifTrue: [ result copyFrom: 2 ]
+    ifFalse: [ result ]
 !
 
 pathFrom: srcName to: destName


--- orig/kernel/FileDescr.st
+++ mod/kernel/FileDescr.st
@@ -103,7 +103,7 @@ open: fileName mode: fileMode
      finished with it anyway, using #close. To keep a file open even when
      no references exist anymore, send it #removeToBeFinalized"
 
-    ((fileName indexOfSubCollection: ':/') > 0 and: [
+    ((fileName indexOfSubCollection: '://') > 0 and: [
         fileMode = FileStream read ]) ifTrue: [
            ^NetClients.URIResolver openStreamOn: fileName ].
 


--- orig/libgst/cint.c
+++ mod/libgst/cint.c
@@ -332,22 +332,6 @@ get_errno (void)
 }
 
 int
-my_utime (const char *name,
-  long new_atime,
-  long new_mtime)
-{
-  struct timeval times[2];
-  int result;
-  times[0].tv_sec = new_atime + 86400 * 10957;
-  times[1].tv_sec = new_mtime + 86400 * 10957;
-  times[0].tv_usec = times[1].tv_usec = 0;
-  result = utimes (name, times);
-  if (!result)
-    errno = 0;
-  return (result);
-}
-
-int
 my_stat (const char *name,
  gst_stat * out)
 {
@@ -539,7 +523,7 @@ _gst_init_cfuncs (void)
   _gst_define_cfunc ("strerror", strerror);
   _gst_define_cfunc ("stat", my_stat);
   _gst_define_cfunc ("lstat", my_lstat);
-  _gst_define_cfunc ("utime", my_utime);
+  _gst_define_cfunc ("utime", _gst_set_file_access_times);
 
   _gst_define_cfunc ("opendir", my_opendir);
   _gst_define_cfunc ("closedir", closedir);


--- orig/libgst/dict.c
+++ mod/libgst/dict.c
@@ -1088,6 +1088,14 @@ init_c_symbols ()
 #define NAN (0.0 / 0.0)
 #endif
 
+#if defined WIN32 && !defined __CYGWIN__
+  NAMESPACE_AT_PUT (cSymbolsOOP, _gst_intern_string ("PathSeparator"),
+    CHAR_OOP_AT ('\\'));
+#else
+  NAMESPACE_AT_PUT (cSymbolsOOP, _gst_intern_string ("PathSeparator"),
+    CHAR_OOP_AT ('/'));
+#endif
+
   NAMESPACE_AT_PUT (cSymbolsOOP, _gst_intern_string ("CDoubleMin"),
     floatd_new (DBL_MIN));
   NAMESPACE_AT_PUT (cSymbolsOOP, _gst_intern_string ("CDoubleMax"),


--- orig/libgst/sysdep.c
+++ mod/libgst/sysdep.c
@@ -745,6 +745,21 @@ _gst_get_cur_dir_name (void)
 }
 
 
+int
+_gst_set_file_access_times (const char *name, long new_atime, long new_mtime)
+{
+  struct timeval times[2];
+  int result;
+  times[0].tv_sec = new_atime + 86400 * 10957;
+  times[1].tv_sec = new_mtime + 86400 * 10957;
+  times[0].tv_usec = times[1].tv_usec = 0;
+  result = utimes (name, times);
+  if (!result)
+    errno = 0;
+  return (result);
+}
+
+
 char *
 _gst_get_full_file_name (const char *fileName)
 {


--- orig/libgst/sysdep.h
+++ mod/libgst/sysdep.h
@@ -138,6 +138,12 @@ extern time_t _gst_get_time (void)
 extern time_t _gst_get_file_modify_time (const char *fileName)
   ATTRIBUTE_HIDDEN;
 
+/* Sets the time when FILENAME was last modified.  The times are in
+   seconds, relative to 1 Jan 2000.  */
+extern int _gst_set_file_access_times (const char *name, long new_atime,
+       long new_mtime)
+  ATTRIBUTE_HIDDEN;
+
 /* Converts the given time (expressed in seconds since midnight Jan 1,
    1970, and in Universal Coordinated Time) into a local time.  */
 extern time_t _gst_adjust_time_zone (time_t t)




--- orig/tests/testsuite
+++ mod/tests/testsuite
@@ -1224,6 +1224,10 @@ else
   at_diff=diff
 fi
 
+if at_diff2=`diff --strip-trailing-cr "$at_devnull" "$at_devnull" 2>&1` && test -z "$at_diff2"
+then
+  at_diff="$at_diff --strip-trailing-cr"
+fi
 
 for at_group in $at_groups
 do

_______________________________________________
help-smalltalk mailing list
[hidden email]
http://lists.gnu.org/mailman/listinfo/help-smalltalk
Reply | Threaded
Open this post in threaded view
|

Re: Building GNU Smalltalk-2.3.5 with MinGW

Paolo Bonzini
In reply to this post by Akeroyd, FA (Freddie)
Akeroyd, FA (Freddie) wrote:
> Thanks for the patches ... unfortunately I've been busier today than I
> though and so haven't been able to try them out properly, but will be
> able to do that next week. With regard to patch 2 for the testsuite, I
> think what you suggest would work but unfortunately the diff supplied
> with MinGW does not seem to support that option. Using "diff
> --ignore-space-change" works, but is not an ideal solution.

Could you check instead if "sed b < foo > bar" has the same effect as
"unix2dos"?

Thanks,

Paolo


_______________________________________________
help-smalltalk mailing list
[hidden email]
http://lists.gnu.org/mailman/listinfo/help-smalltalk
Reply | Threaded
Open this post in threaded view
|

RE: Building GNU Smalltalk-2.3.5 with MinGW

Akeroyd, FA (Freddie)
In reply to this post by Akeroyd, FA (Freddie)

> The attached patch, on top of 2.3.5, is my take on this.  It fixes all

> path issues, so the only things left should be:

I've rebuilt my MinGW version using the supplied patches and the program
compiles and creates an image OK. There are, however, two test failures
on a make check (quit.st and fileext.st). The quit test is probably to
do with buffer flushing at program exit and I will look at that; the
details of the filext failure are:

18. testsuite.at:44: testing ...
./testsuite.at:44: cd $abs_srcdir && $GST -r fileext.st 2>&1
--- expout Mon Jun 18 13:54:50 2007
+++ tests/testsuite.dir/at-stdout Mon Jun 18 13:54:50 2007
@@ -11,18 +11,18 @@
 true
 true
 true
+false
 true
 true
 true
 true
+false
 true
 true
 true
 true
 true
-true
-true
-true
+false
 true
 true
 true
18. testsuite.at:44: 18. fileext.st (testsuite.at:44): FAILED
(testsuite.at:44)

Also if I try to rebuild the documentation with

touch kernel/File.st
make

It fails with the following error:

Making all in doc
make[2]: Entering directory
`/home/faa59/Smalltalk_gnu/smalltalk-2.3.5/doc'
rm -f ./classes.texi
builddir=`pwd`; gst=$builddir/../gst; gst_im=$builddir/../gst.im; \
cd . && \
  $gst -I $gst_im -f ../scripts/GenBaseDoc.st \
  Smalltalk SystemExceptions NetClients VFS
writing documentation for AbstractNamespace
Object: FileStream error: could not open
C:\msys\1.0\home\faa59\Smalltalk_gnu\smalltalk-2.3.5/C:/msys/1.0/home/fa
a59/Smalltalk_gnu/smalltalk-2.3.5/kernel/AbstNamespc.st
SystemExceptions.FileError(Exception)>>#signal
SystemExceptions.FileError class(Exception class)>>#signal:
[] in FileStream class(FileDescriptor class)>>#open:mode:
[] in FileStream class(FileDescriptor class)>>#fopen:mode:ifFail:
FileStream(FileDescriptor)>>#fileOp:with:with:ifFail:
FileStream class(FileDescriptor class)>>#fopen:mode:ifFail:
VFS.RealFileHandler>>#open:mode:ifFail:
FileStream class(FileDescriptor class)>>#open:mode:
FileSegment>>#withFileDo:
FileSegment>>#asString
MethodInfo>>#sourceString
 

> Could you check instead if "sed b < foo > bar" has the same effect as
"unix2dos"?

Unfortunately not - no \r characters are added to the lines and so the
tests still fail. However the Windows putchar() function intercepts a
bare \n and substitutes \r\n so the following piece of C code will do
the conversion on windows and leave things unchanged on unix:

#include <stdio.h>
int main(int argc, char* argv[])
{
    int c;
    while( (c = getchar()) != EOF )
    {
        putchar(c);
    }
    return 0;
}

> modifying _gst_set_file_access_times to use the appropriate Windows
API function

Windows provides an implementation of the POSIX utime() function which
should do the job for us. I notice the current code uses utimes() rather
than utime() - is utimes() generally more widely available or is this
usage purely for historical reasons?

Freddie



_______________________________________________
help-smalltalk mailing list
[hidden email]
http://lists.gnu.org/mailman/listinfo/help-smalltalk
Reply | Threaded
Open this post in threaded view
|

Re: Building GNU Smalltalk-2.3.5 with MinGW

Paolo Bonzini

> Object: FileStream error: could not open
> C:\msys\1.0\home\faa59\Smalltalk_gnu\smalltalk-2.3.5/C:/msys/1.0/home/fa
> a59/Smalltalk_gnu/smalltalk-2.3.5/kernel/AbstNamespc.st

You should find out how the problematic path is built (see
kernel/MethodInfo.st as well as examples/Publish.st).  You can try

(AbstractNamespace >> #superspace) methodSourceCode fileName

to see if the bad path is generated by GNU Smalltalk itself, or rather
by something in kernel/File.st or kernel/Directory.st (in which case
there is something more to fix there). I tried the obvious test:

Directory append:
'C:/msys/1.0/home/faa59/Smalltalk_gnu/smalltalk-2.3.5/kernel/AbstNamespc.st'
to: 'C:\msys\1.0\home\faa59\Smalltalk_gnu\smalltalk-2.3.5'

but it gave correctly
'C:/msys/1.0/home/faa59/Smalltalk_gnu/smalltalk-2.3.5/kernel/AbstNamespc.st'

>> Could you check instead if "sed b < foo > bar" has the same effect as
> "unix2dos"?
>
> Unfortunately not - no \r characters are added to the lines and so the
> tests still fail. However the Windows putchar() function intercepts a
> bare \n and substitutes \r\n so the following piece of C code will do
> the conversion on windows and leave things unchanged on unix:

Okay, then I prefer stripping \r from GNU Smalltalk's output. :-)

>> modifying _gst_set_file_access_times to use the appropriate Windows
>> API function
>
> Windows provides an implementation of the POSIX utime() function which
> should do the job for us. I notice the current code uses utimes() rather
> than utime() - is utimes() generally more widely available or is this
> usage purely for historical reasons?

utime provides only 1-second resolution.  That's fine for GNU Smalltalk
though.

The attached patch (to be applied on top of the previous one) implements
this.

Paolo

--- orig/configure.ac
+++ mod/configure.ac
@@ -186,7 +186,7 @@ AC_DEFINE(_GNU_SOURCE, 1, [We want the d
 AC_HEADER_ASSERT
 AC_CHECK_HEADERS_ONCE(stdint.h inttypes.h unistd.h poll.h sys/ioctl.h \
  sys/resource.h sys/utsname.h stropts.h sys/param.h stddef.h limits.h \
- sys/timeb.h termios.h sys/mman.h sys/file.h execinfo.h \
+ sys/timeb.h termios.h sys/mman.h sys/file.h execinfo.h utime.h \
  sys/wait.h fcntl.h, [], [], [AC_INCLUDES_DEFAULT])
 
 AC_TYPE_INT8_T
@@ -215,7 +215,7 @@ AC_REPLACE_FUNCS(putenv strdup strerror
  getdtablesize strstr ftruncate floorl ceill sqrtl frexpl ldexpl asinl \
  acosl atanl logl expl tanl sinl cosl truncl lrintl strsep strpbrk)
 AC_CHECK_FUNCS_ONCE(gethostname memcpy memmove sighold uname sbrk usleep lstat \
- grantpt popen getrusage gettimeofday getcwd fork strchr utimes \
+ grantpt popen getrusage gettimeofday getcwd fork strchr utimes utime \
  sigsetmask alarm select mprotect madvise nl_langinfo waitpid \
  setsid spawnl nanosleep pread pwrite)
 


--- orig/libgst/sysdep.c
+++ mod/libgst/sysdep.c
@@ -58,6 +58,10 @@
 
 #include "gstpriv.h"
 
+#ifdef HAVE_UTIME_H
+# include <utime.h>
+#endif
+
 #ifdef HAVE_SYS_TIMES_H
 # include <sys/times.h>
 #endif
@@ -745,11 +749,22 @@ _gst_get_cur_dir_name (void)
 _gst_set_file_access_times (const char *name, long new_atime, long new_mtime)
 {
   int result;
+#if defined HAVE_UTIMES
   struct timeval times[2];
   times[0].tv_sec = new_atime + 86400 * 10957;
   times[1].tv_sec = new_mtime + 86400 * 10957;
   times[0].tv_usec = times[1].tv_usec = 0;
   result = utimes (name, times);
+#elif defined HAVE_UTIME
+  struct utimbuf utb;
+  utb.actime = new_atime + 86400 * 10957;
+  utb.modtime = new_mtime + 86400 * 10957;
+  result = utime (name, &utb);
+#else
+#warning neither utime nor utimes are available.
+  errno = ENOSYS;
+  result = -1;
+#endif
   if (!result)
     errno = 0;
   return (result);

--- orig/tests/fileext.st
+++ mod/tests/fileext.st
@@ -72,4 +72,5 @@ testStripExtensionFrom
  [(File stripExtensionFrom: each key),
  (File extensionFor: each key) = each key] value printNl ]! !
 
+CSymbols.PathSeparator := $/.
 Object new testExtensionFor; testStripExtensionFrom!


--- orig/tests/local.at
+++ mod/tests/local.at
@@ -25,7 +25,7 @@ m4_define([AT_CHECK_GST], [
     *) GST="$AUTOTEST_PATH/gst m4_ifval([$2], [-I $2])" ;;
   esac
 
-  AT_CHECK([cd m4_ifval([$3], [$3], [$abs_top_builddir]) && $GST $1], 0, [$4], [$5])
+  AT_CHECK([cd m4_ifval([$3], [$3], [$abs_top_builddir]) && $GST $1 | tr -d '\r'], 0, [$4], [$5])
 ])
 
 dnl AT_DIFF_TEST([FILE], [XFAILS])



_______________________________________________
help-smalltalk mailing list
[hidden email]
http://lists.gnu.org/mailman/listinfo/help-smalltalk
Reply | Threaded
Open this post in threaded view
|

RE: Building GNU Smalltalk-2.3.5 with MinGW

Akeroyd, FA (Freddie)
Hi,

> You should find out how the problematic path is built (see
> kernel/MethodInfo.st as well as examples/Publish.st).  You can try

> (AbstractNamespace >> #superspace) methodSourceCode fileName

> to see if the bad path is generated by GNU Smalltalk itself, or rather


This gave

'C:\msys\1.0\home\faa59\Smalltalk_gnu\smalltalk-2.3.5/C:/msys/1.0/home/f
aa59/Smalltalk_gnu/smalltalk-2.3.5/kernel/AbstNamespc.st'

I applied the enclosed patch to File.st and that fixed the "make doc" of
the library, but it is not the end of the story as now rebuilding the
Blox documentation fails with invalid paths. The File.st patch does not
make the methodSourceCode filename above correct, it just allows
Smalltalk to handle it in the library case.

I think the cause of the problem is illustrated by running:

(File fullNameFor: 'c:\some\rubbish\c:\windows') printNl!

Which returns

c:\windows

So (Directory exists: 'c:\some\rubbish\c:\windows') will return true. I
believe the Blox doc issue occurs as the paths being built up in the
baseDirs method of the Package are using "Directory exists:" and thus
getting told incorrect information which they then store.

The root of the problem probably lies with how to treat c: when it is
detected in the "Directory append:" method as bits of a path are passed
to it. In the above example the first c: should indicate the start an
absolute path, but not the second c: as that then leads to an incorrect
result.

Freddie


_______________________________________________
help-smalltalk mailing list
[hidden email]
http://lists.gnu.org/mailman/listinfo/help-smalltalk

File.patch (966 bytes) Download Attachment
Reply | Threaded
Open this post in threaded view
|

Re: Building GNU Smalltalk-2.3.5 with MinGW

Paolo Bonzini
Akeroyd, FA (Freddie) wrote:

> Hi,
>
>> You should find out how the problematic path is built (see
>> kernel/MethodInfo.st as well as examples/Publish.st).  You can try
>
>> (AbstractNamespace >> #superspace) methodSourceCode fileName
>
>> to see if the bad path is generated by GNU Smalltalk itself, or rather
>
>
> This gave
>
> 'C:\msys\1.0\home\faa59\Smalltalk_gnu\smalltalk-2.3.5/C:/msys/1.0/home/f
> aa59/Smalltalk_gnu/smalltalk-2.3.5/kernel/AbstNamespc.st'
>
> I applied the enclosed patch to File.st

The patch is fine, I'm applying it.

The bug you found in fullNameFor: is also real; to fix it, you can
simply use "old, self pathSeparatorString, each" instead of "Directory
append: each to: old".

The real problem however is in _gst_get_full_file_name, which also needs
to know about Windows paths.  Something like this should do (in
libgst/sysdep.c):

char *
_gst_get_full_file_name (const char *fileName)
{
   char *fullFileName;
   static char *fullPath = NULL;

   /* Absolute paths don't need to change */
   if (fileName[0] == '/')
     return (xstrdup (fileName));
#if defined WIN32 && !defined __CYGWIN__
   if (fileName[0] == '\\' || (fileName[0] != '\0' && fileName[1] == ':'))
     return (xstrdup (fileName));
#endif

   /* Only need to do this once, then cache the result */
   if (fullPath == NULL)
     fullPath = _gst_get_cur_dir_name ();

#if !defined WIN32 || defined __CYGWIN__
   asprintf (&fullFileName, "%s/%s", fullPath, fileName);
#else
   asprintf (&fullFileName, "%s\\%s", fullPath, fileName);
#endif

   return (fullFileName);
}

For 3.0 I will use the Win32 API function GetFullPathName (this piece of
code changed completely), but for now this should be enough.

Paolo


_______________________________________________
help-smalltalk mailing list
[hidden email]
http://lists.gnu.org/mailman/listinfo/help-smalltalk
Reply | Threaded
Open this post in threaded view
|

Re: Building GNU Smalltalk-2.3.5 with MinGW

S11001001
On Tue, 2007-06-19 at 14:22 +0200, Paolo Bonzini wrote:
> The bug you found in fullNameFor: is also real; to fix it, you can
> simply use "old, self pathSeparatorString, each" instead of "Directory

Or, better yet, "{old. self pathSeparatorString. each} joinAll", in
devo. :)

--
;;; Stephen Compall ** http://scompall.nocandysw.com/blog **
"Peta" is Greek for fifth; a petabyte is 10 to the fifth power, as
well as fifth in line after kilo, mega, giga, and tera.
  -- Lee Gomes, performing every Wednesday in his tech column
     "Portals" on page B1 of The Wall Street Journal

_______________________________________________
help-smalltalk mailing list
[hidden email]
http://lists.gnu.org/mailman/listinfo/help-smalltalk

signature.asc (196 bytes) Download Attachment
Reply | Threaded
Open this post in threaded view
|

Re: Building GNU Smalltalk-2.3.5 with MinGW

Paolo Bonzini
In reply to this post by Paolo Bonzini
Akeroyd, FA (Freddie) wrote:
> Hi,
>
> Your suggestions seem to sort everything out - thanks. I'll see if I can
> get everything into a patch kit for you today, but otherwise it will be
> the end of next week as I'm away from lunchtime today.

Thanks!

Paolo



_______________________________________________
help-smalltalk mailing list
[hidden email]
http://lists.gnu.org/mailman/listinfo/help-smalltalk