mirror of
https://github.com/ksherlock/mpw-shell.git
synced 2025-01-06 21:32:07 +00:00
directory -- support for MacOS pathnames.
This commit is contained in:
parent
acf616845e
commit
3fea71d1e8
@ -6,7 +6,7 @@ project("mpw-shell")
|
||||
set (PROJECT_TYPE "CXX")
|
||||
set (PROJECT_NAME "MPW Shell")
|
||||
|
||||
set(CMAKE_CXX_FLAGS "-g -Wall -Wno-unused-variable -Wno-multichar")
|
||||
set(CMAKE_CXX_FLAGS "-g -Wall -Wno-unused-variable -Wno-multichar -O1")
|
||||
|
||||
if(${CMAKE_CXX_COMPILER_ID} MATCHES "Clang")
|
||||
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wno-unused-const-variable ")
|
||||
@ -66,6 +66,7 @@ endmacro()
|
||||
RAGEL_TARGET(mpw-shell-read mpw-shell-read.rl mpw-shell-read.cpp COMPILE_FLAGS "-p -G2")
|
||||
RAGEL_TARGET(phase1 phase1.rl phase1.cpp COMPILE_FLAGS "-p -G2")
|
||||
RAGEL_TARGET(phase2 phase2.rl phase2.cpp COMPILE_FLAGS "-p -G2")
|
||||
RAGEL_TARGET(pathnames pathnames.rl pathnames.cpp COMPILE_FLAGS "-p -G2")
|
||||
|
||||
# need to copy all OUTPUT file to the build dir
|
||||
add_custom_command(
|
||||
@ -113,7 +114,8 @@ add_custom_command(
|
||||
# mpw-shell-execute.cpp mpw-shell-builtins.cpp mpw-shell-read.cpp
|
||||
add_executable(mpw-shell mpw-shell.cpp mpw-shell-token.cpp mpw-shell-expand.cpp
|
||||
mpw-shell-parser.cpp value.cpp mpw-shell-quote.cpp
|
||||
phase1.cpp phase2.cpp phase2-parser.cpp command.cpp environment.cpp builtins.cpp mapped_file.cpp)
|
||||
phase1.cpp phase2.cpp phase2-parser.cpp command.cpp environment.cpp builtins.cpp mapped_file.cpp
|
||||
pathnames.cpp)
|
||||
|
||||
target_link_libraries(mpw-shell edit)
|
||||
|
||||
|
10
builtins.cpp
10
builtins.cpp
@ -15,6 +15,12 @@
|
||||
//MAXPATHLEN
|
||||
#include <sys/param.h>
|
||||
|
||||
|
||||
namespace ToolBox {
|
||||
std::string MacToUnix(const std::string path);
|
||||
std::string UnixToMac(const std::string path);
|
||||
}
|
||||
|
||||
namespace {
|
||||
|
||||
/*
|
||||
@ -46,6 +52,7 @@ namespace {
|
||||
|
||||
}
|
||||
|
||||
|
||||
#undef stdin
|
||||
#undef stdout
|
||||
#undef stderr
|
||||
@ -330,7 +337,8 @@ int builtin_directory(Environment &env, const std::vector<std::string> &tokens,
|
||||
}
|
||||
|
||||
// todo -- pathname translation.
|
||||
int ok = chdir(argv.front().c_str());
|
||||
std::string path = ToolBox::MacToUnix(argv.front());
|
||||
int ok = chdir(path.c_str());
|
||||
if (ok < 0) {
|
||||
fputs("### Directory - Unable to set current directory.\n", stderr);
|
||||
perror("chdir: ");
|
||||
|
267
pathnames.rl
Normal file
267
pathnames.rl
Normal file
@ -0,0 +1,267 @@
|
||||
/*
|
||||
* Copyright (c) 2013, Kelvin W Sherlock
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
|
||||
* ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||
* (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
* LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
|
||||
* ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
#include <string>
|
||||
|
||||
//#include "toolbox.h"
|
||||
|
||||
|
||||
|
||||
namespace {
|
||||
|
||||
|
||||
/*
|
||||
* To Mac:
|
||||
* file -> file
|
||||
* :directory:file -> directory/file
|
||||
* volume:directory -> /volume/directory
|
||||
* : -> ./
|
||||
* :: -> ../
|
||||
* ::: -> ../../
|
||||
*
|
||||
* To Unix:
|
||||
* file -> file
|
||||
* directory/file -> :directory:file
|
||||
* /volume/file -> volume:file
|
||||
*
|
||||
*/
|
||||
|
||||
|
||||
%%{
|
||||
machine mac;
|
||||
|
||||
main := |*
|
||||
|
||||
':' {2,} {
|
||||
|
||||
// :: = ..
|
||||
// ::: = ../..
|
||||
// etc
|
||||
unsigned count = te - ts;
|
||||
|
||||
if (ts != begin)
|
||||
{
|
||||
rv.push_back('/');
|
||||
}
|
||||
for (unsigned i = 1; i < count; ++i)
|
||||
{
|
||||
rv.append("../");
|
||||
}
|
||||
};
|
||||
|
||||
':' {
|
||||
/*
|
||||
if (ts == begin)
|
||||
rv.append("./");
|
||||
else
|
||||
rv.push_back('/');
|
||||
*/
|
||||
if (ts != begin)
|
||||
rv.push_back('/');
|
||||
};
|
||||
|
||||
|
||||
any {
|
||||
rv.push_back(*ts);
|
||||
};
|
||||
|
||||
*|;
|
||||
|
||||
write data;
|
||||
}%%
|
||||
|
||||
%%{
|
||||
machine unix;
|
||||
|
||||
main := |*
|
||||
|
||||
'/' + {
|
||||
// collapse multiple /s to a single ':'
|
||||
if (ts != begin)
|
||||
{
|
||||
rv.push_back(':');
|
||||
slash = true;
|
||||
}
|
||||
};
|
||||
|
||||
any {
|
||||
rv.push_back(*ts);
|
||||
};
|
||||
|
||||
*|;
|
||||
|
||||
write data;
|
||||
}%%
|
||||
|
||||
}
|
||||
|
||||
namespace ToolBox
|
||||
{
|
||||
|
||||
std::string MacToUnix(const std::string path)
|
||||
{
|
||||
|
||||
// todo -- Dev:Null -> lowercase it?
|
||||
|
||||
int sep = 0;
|
||||
bool colon = false;
|
||||
|
||||
for (char c : path)
|
||||
{
|
||||
switch (c)
|
||||
{
|
||||
case ':':
|
||||
colon = true;
|
||||
case '/':
|
||||
if (!sep) sep = c;
|
||||
break;
|
||||
|
||||
}
|
||||
if (colon) break;
|
||||
}
|
||||
|
||||
// no colon - no problem.
|
||||
if (!colon) return path;
|
||||
|
||||
// special case ":" -> "."
|
||||
if (colon && path.length() == 1) return ".";
|
||||
|
||||
const char *p = path.c_str();
|
||||
const char *pe = p + path.length();
|
||||
const char *eof = pe;
|
||||
const char *ts;
|
||||
const char *te;
|
||||
|
||||
const char *begin = p;
|
||||
int cs;
|
||||
int act;
|
||||
|
||||
std::string rv;
|
||||
|
||||
// volume:directory -> /volume
|
||||
if (sep == ':' && path.front() != ':')
|
||||
rv.push_back('/');
|
||||
|
||||
%%{
|
||||
machine mac;
|
||||
|
||||
write init;
|
||||
write exec;
|
||||
}%%
|
||||
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
||||
std::string UnixToMac(const std::string path)
|
||||
{
|
||||
// /volume/directory -> volume:directory
|
||||
// // -> /
|
||||
|
||||
|
||||
bool slash = false;
|
||||
bool sep = 0;
|
||||
|
||||
for (char c : path)
|
||||
{
|
||||
switch(c)
|
||||
{
|
||||
case '/':
|
||||
slash = true;
|
||||
case ':':
|
||||
if (!sep) sep = c;
|
||||
break;
|
||||
}
|
||||
if (slash) break;
|
||||
}
|
||||
|
||||
if (!slash) return path;
|
||||
|
||||
const char *p = path.c_str();
|
||||
const char *pe = p + path.length();
|
||||
const char *eof = pe;
|
||||
const char *ts;
|
||||
const char *te;
|
||||
|
||||
const char *begin = p;
|
||||
int act;
|
||||
int cs;
|
||||
|
||||
std::string rv;
|
||||
|
||||
|
||||
slash = false;
|
||||
// path/file -> :path:file
|
||||
if (path.front() != '/')
|
||||
{
|
||||
rv.push_back(':');
|
||||
slash = true;
|
||||
}
|
||||
%%{
|
||||
machine unix;
|
||||
|
||||
write init;
|
||||
write exec;
|
||||
}%%
|
||||
|
||||
// special check /dir -> dir:
|
||||
if (path.front() == '/' && !slash) rv.push_back(':');
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
#ifdef TESTING
|
||||
|
||||
#include <cstdio>
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
|
||||
for (int i = 1; i < argc; ++i)
|
||||
{
|
||||
std::string s(argv[i]);
|
||||
std::string a = ToolBox::MacToUnix(s);
|
||||
std::string b = ToolBox::UnixToMac(s);
|
||||
|
||||
if (s != a)
|
||||
printf("ToUnix: %s -> %s\n", s.c_str(), a.c_str());
|
||||
|
||||
if (s != b)
|
||||
printf("ToMac: %s -> %s\n", s.c_str(), b.c_str());
|
||||
|
||||
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif
|
Loading…
Reference in New Issue
Block a user