He creado un programa C simple así:
int main(int argc, char *argv[]) {
if (argc != 5) {
fputs("Not enough arguments!\n", stderr);
exit(EXIT_FAILURE);
}
Y tengo mi RUTA modificada en etc / bash.bashrc así:
PATH=.:$PATH
He guardado este programa como set.c y lo estoy compilando con
gcc -o set set.c
en la carpeta
~/Programming/so
Sin embargo, cuando llamo
set 2 3
no pasa nada. No hay texto que aparezca.
Vocación
./set 2 3
da el resultado esperado
Nunca he tenido un problema con PATH antes y
which set
vuelve ./set. Entonces parece que la RUTA es la correcta. ¿Qué está pasando?
shell
path
shell-builtin
Ganea Dan Andrei
fuente
fuente

testbásicamente por la misma razón;testTambién es un shell incorporado.testparece tener sentido. Por supuesto, para cuando lo coloques en tuPATHrealmente deberías haber encontrado un nombre diferente. Y hasta que ponga el programa en suPATHcuenta, deberá invocarlo como de./testtodos modos. Por lo tanto, está bien usar el nombretestde un programa siempre que sea una prueba rápida que intente eliminar antes de que finalice el día.foo.lscada vez que vaya a ver si existe, se ejecutará (pero solo si modifica su ruta como lo hizo en la pregunta).Respuestas:
En lugar de usar
which, que no funciona cuando más lo necesita , usetypepara determinar qué se ejecutará cuando escriba un comando:El shell siempre busca incorporaciones antes de buscar
$PATH, por lo que la configuración$PATHno ayuda aquí.Sería mejor cambiar el nombre de su ejecutable a otra cosa, pero si su asignación requiere que se nombre el programa
set, puede usar una función de shell:(Eso funciona
bash, pero otros shells comokshpueden no permitirlo. Vea la respuesta de mikeserv para una solución más portátil).Ahora escribiendo
setse ejecutará la función llamada "set", que se ejecuta./set. GNUbashbusca funciones antes de buscar builtins, y busca builtins antes de buscar el$PATH. La sección denominada "EJECUCIÓN DE MANDOS" en la página del manual de bash brinda más información al respecto.Consulte también la documentación sobre
builtinycommand:help builtinyhelp command.fuente
typemáswhich, pero no des ninguna razón por qué. ( Sé por qué , pero alguien que necesita la recomendación no lo haría.)typelugar dewhich, no asigne un nombre a su programa "set", y comprenda quefunction set { ./set; }es un truco feo que probablemente debería evitar.setes un incorporado en bash (y probablemente en la mayoría de las otras conchas). Esto significa que bash ni siquiera buscará la ruta cuando busque la función.Como comentario adicional, recomendaría encarecidamente no agregar
.al camino por razones de seguridad. Imagine, por ejemplocd, salir/tmpdespués de que cualquier otro usuario agregue un archivo ejecutable/tmp/cd.fuente
cdes un shell incorporado, por lo que el ejemplo no funcionará por la misma razón que conset../foopara invocar un programa es profesional; muestra que entiendes por.qué no debería estar en $ PATH. Tu maestro está equivocado, y puedes decirle que lo dije.setno es solo una construcción integrada, es una construcción especial POSIX . Hay algunas órdenes internas que son estándares especificados que se encuentran en una búsqueda de comandos antes de cualquier otra cosa -$PATHno se busca, nombres de funciones no se buscan, y etc. La mayoría de las órdenes internas que son no especiales están realmente requerido por el estándar POSIX sean encontrado en su$PATHantes de que el shell ejecute cualquiera de sus propios procedimientos integrados. Este es el caso deechoy la mayoría de los demás (aunque si la norma es honrado en este sentido ha sido un tema de discusión en las listas de correo de grupo abierto en el pasado) , pero no deset,trap,break,return,continue,.,:,times,eval,exit,export,readonly,unset, Oexec.Todos estos son nombres reservados del shell, y también tienen atributos especiales además de su orden de preferencia para la búsqueda de comandos. Por ejemplo, no puede definir una función de shell con ninguno de esos nombres en un shell compatible con los estándares. Esto es algo bueno : permite a las personas escribir scripts portátiles de forma segura . Estos son comandos de línea de base desde los cuales un escritor de guiones experimentado puede establecer un punto de apoyo seguro y confiable en su entorno. Invadir este espacio de nombres no es aconsejable.
Sin embargo, si desea invadirlo, puede hacerlo de forma portátil
alias. El orden de expansión de shell permite esta solución. Debido a quealiasse expande mientras se lee el comando, lo que sea que reemplace elsetnombre en su definición se expandirá correctamente, probablemente no debería expandirse a uno de esos nombres.Entonces podrías hacer:
... que funcionará bien.
fuente
El problema es que
setes un shell integrado y la mejor solución sería usar un nombre diferente para su programa ejecutable.Por cierto, la semana pasada, hice una pregunta sobre cómo ejecutar los comandos del sistema en lugar de los shell incorporados con el mismo nombre y la solución que acepté fue ejecutar el comando a través de
env:Para este caso en particular, donde ya sabe que el comando que desea usar se encuentra en su directorio actual, sería mejor ejecutar directamente el ejecutable ingresando su ruta (usando
.para representar el directorio de trabajo actual):Ambas soluciones anteriores son independientes de la shell, es decir, funcionarán independientemente de la shell que esté utilizando.
Sugerencias como el uso de la función
commandintegrada no funcionarán en Bash: esto solo evita que se ejecuten las funciones de shell . Si bien no está documentado, también he notado que el usocommandtambién suprime las palabras clave de shell . Sin embargo, no hará lo mismo para las construcciones de shell comoset. Según tengo entendido,commandpuede funcionar con otros shells como zsh.Además, trucos tales como
\seto"set", o'set'no lo hacen el trabajo de órdenes internas del golpe - a pesar de que son útiles para la ejecución de archivos ejecutables en lugar de alias o de concha palabras clave .Nota: Esta respuesta originalmente comenzó como un comentario sobre la respuesta (aceptada) de Eric, pero se hizo demasiado grande para caber en un comentario. Las otras respuestas que recomiendan usar
typey no agregar.a la RUTA son buenas.fuente