1
0
mirror of https://github.com/samba-team/samba.git synced 2025-03-25 14:50:24 +03:00

first public release of samba4 code

(This used to be commit b0510b5428b3461aeb9bbe3cc95f62fc73e2b97f)
This commit is contained in:
Andrew Tridgell 2003-08-13 01:53:07 +00:00
commit ef2e26c91b
779 changed files with 352638 additions and 0 deletions

34
source4/.cvsignore Normal file
View File

@ -0,0 +1,34 @@
libsmb
*.po
*.po32
.headers.stamp
.inslog2
.ix*
.proto.check
.proto.stamp
autom4te.cache
ID
ID
Makefile
bin
build
config.cache
config.log
config.status
configure.tridge
cvs.log
diffs
dmalloc.log
dmallog.log
dox
libtool
so_locations
tca.log
testdir
testtmp
trace.out
typescript*
configure
config.jjm
config.stfs
*.dat

2
source4/.dmallocrc Normal file
View File

@ -0,0 +1,2 @@
samba allow-free-null, log-stats, log-non-free, log-trans, \
check-fence, check-heap, check-lists, error-abort

176
source4/Doxyfile Normal file
View File

@ -0,0 +1,176 @@
# Doxyfile 0.1
#---------------------------------------------------------------------------
# General configuration options
#---------------------------------------------------------------------------
PROJECT_NAME = Samba
PROJECT_NUMBER = HEAD
# NOTE: By default, Doxygen writes into the dox/ subdirectory of the
# invocation directory. If you want to put it somewhere else, for
# example, to write straight into a webserver directory, then override
# this variable in a configuration concatenated to this one: Doxygen
# doesn't mind variables being redefined.
OUTPUT_DIRECTORY = dox
OUTPUT_LANGUAGE = English
EXTRACT_ALL = YES
EXTRACT_PRIVATE = YES
EXTRACT_STATIC = YES
HIDE_UNDOC_MEMBERS = NO
HIDE_UNDOC_CLASSES = NO
BRIEF_MEMBER_DESC = YES
REPEAT_BRIEF = YES
ALWAYS_DETAILED_SEC = NO
FULL_PATH_NAMES = YES
STRIP_FROM_PATH = $(PWD)/
INTERNAL_DOCS = YES
CLASS_DIAGRAMS = YES
SOURCE_BROWSER = YES
INLINE_SOURCES = YES
STRIP_CODE_COMMENTS = NO
CASE_SENSE_NAMES = YES
SHORT_NAMES = NO
HIDE_SCOPE_NAMES = YES
VERBATIM_HEADERS = YES
SHOW_INCLUDE_FILES = YES
JAVADOC_AUTOBRIEF = YES
INHERIT_DOCS = YES
INLINE_INFO = YES
SORT_MEMBER_DOCS = NO
DISTRIBUTE_GROUP_DOC = NO
TAB_SIZE = 8
GENERATE_TODOLIST = YES
GENERATE_TESTLIST = YES
GENERATE_BUGLIST = YES
ALIASES =
ENABLED_SECTIONS =
MAX_INITIALIZER_LINES = 30
OPTIMIZE_OUTPUT_FOR_C = YES
SHOW_USED_FILES = YES
REFERENCED_BY_RELATION = YES
#---------------------------------------------------------------------------
# configuration options related to warning and progress messages
#---------------------------------------------------------------------------
QUIET = YES
WARNINGS = NO
WARN_IF_UNDOCUMENTED = NO
WARN_FORMAT = "$file:$line: $text"
WARN_LOGFILE =
#---------------------------------------------------------------------------
# configuration options related to the input files
#---------------------------------------------------------------------------
INPUT = .
FILE_PATTERNS = *.c \
*.h \
*.idl
RECURSIVE = YES
EXCLUDE = include/includes.h \
include/proto.h
EXCLUDE_PATTERNS =
EXAMPLE_PATH =
EXAMPLE_PATTERNS =
IMAGE_PATH =
INPUT_FILTER =
FILTER_SOURCE_FILES = NO
#---------------------------------------------------------------------------
# configuration options related to the alphabetical class index
#---------------------------------------------------------------------------
ALPHABETICAL_INDEX = YES
COLS_IN_ALPHA_INDEX = 1
IGNORE_PREFIX =
#---------------------------------------------------------------------------
# configuration options related to the HTML output
#---------------------------------------------------------------------------
GENERATE_HTML = YES
HTML_OUTPUT = .
HTML_HEADER =
HTML_FOOTER =
HTML_STYLESHEET =
HTML_ALIGN_MEMBERS = YES
GENERATE_HTMLHELP = NO
GENERATE_CHI = NO
BINARY_TOC = NO
TOC_EXPAND = NO
DISABLE_INDEX = NO
ENUM_VALUES_PER_LINE = 3
GENERATE_TREEVIEW = NO
TREEVIEW_WIDTH = 250
#---------------------------------------------------------------------------
# configuration options related to the LaTeX output
#---------------------------------------------------------------------------
GENERATE_LATEX = NO
LATEX_OUTPUT = latex
COMPACT_LATEX = NO
PAPER_TYPE = a4wide
EXTRA_PACKAGES =
LATEX_HEADER =
PDF_HYPERLINKS = YES
USE_PDFLATEX = YES
LATEX_BATCHMODE = YES
#---------------------------------------------------------------------------
# configuration options related to the RTF output
#---------------------------------------------------------------------------
GENERATE_RTF = NO
RTF_OUTPUT = rtf
COMPACT_RTF = NO
RTF_HYPERLINKS = NO
RTF_STYLESHEET_FILE =
RTF_EXTENSIONS_FILE =
#---------------------------------------------------------------------------
# configuration options related to the man page output
#---------------------------------------------------------------------------
GENERATE_MAN = NO
MAN_OUTPUT = man
MAN_EXTENSION = .3
MAN_LINKS = NO
#---------------------------------------------------------------------------
# configuration options related to the XML output
#---------------------------------------------------------------------------
GENERATE_XML = NO
#---------------------------------------------------------------------------
# configuration options related to the preprocessor
#---------------------------------------------------------------------------
ENABLE_PREPROCESSING = NO
MACRO_EXPANSION = NO
EXPAND_ONLY_PREDEF = NO
SEARCH_INCLUDES = YES
INCLUDE_PATH =
INCLUDE_FILE_PATTERNS =
PREDEFINED =
EXPAND_AS_DEFINED =
SKIP_FUNCTION_MACROS = YES
#---------------------------------------------------------------------------
# configuration::additions related to external references
#---------------------------------------------------------------------------
TAGFILES =
GENERATE_TAGFILE =
ALLEXTERNALS = NO
PERL_PATH = /usr/bin/perl
#---------------------------------------------------------------------------
# configuration options related to the dot tool
#---------------------------------------------------------------------------
HAVE_DOT = NO
CLASS_GRAPH = YES
COLLABORATION_GRAPH = YES
TEMPLATE_RELATIONS = YES
INCLUDE_GRAPH = YES
INCLUDED_BY_GRAPH = YES
GRAPHICAL_HIERARCHY = YES
DOT_PATH =
DOTFILE_DIRS =
MAX_DOT_GRAPH_WIDTH = 1024
MAX_DOT_GRAPH_HEIGHT = 1024
GENERATE_LEGEND = YES
DOT_CLEANUP = YES
#---------------------------------------------------------------------------
# configuration::additions related to the search engine
#---------------------------------------------------------------------------
SEARCHENGINE = NO
CGI_NAME = search.cgi
CGI_URL =
DOC_URL =
DOC_ABSPATH =
BIN_ABSPATH = /usr/local/bin/
EXT_DOC_PATHS =

1338
source4/Makefile.in Normal file

File diff suppressed because it is too large Load Diff

643
source4/aclocal.m4 vendored Normal file
View File

@ -0,0 +1,643 @@
dnl AC_VALIDATE_CACHE_SYSTEM_TYPE[(cmd)]
dnl if the cache file is inconsistent with the current host,
dnl target and build system types, execute CMD or print a default
dnl error message.
AC_DEFUN(AC_VALIDATE_CACHE_SYSTEM_TYPE, [
AC_REQUIRE([AC_CANONICAL_SYSTEM])
AC_MSG_CHECKING([config.cache system type])
if { test x"${ac_cv_host_system_type+set}" = x"set" &&
test x"$ac_cv_host_system_type" != x"$host"; } ||
{ test x"${ac_cv_build_system_type+set}" = x"set" &&
test x"$ac_cv_build_system_type" != x"$build"; } ||
{ test x"${ac_cv_target_system_type+set}" = x"set" &&
test x"$ac_cv_target_system_type" != x"$target"; }; then
AC_MSG_RESULT([different])
ifelse($#, 1, [$1],
[AC_MSG_ERROR(["you must remove config.cache and restart configure"])])
else
AC_MSG_RESULT([same])
fi
ac_cv_host_system_type="$host"
ac_cv_build_system_type="$build"
ac_cv_target_system_type="$target"
])
dnl test whether dirent has a d_off member
AC_DEFUN(AC_DIRENT_D_OFF,
[AC_CACHE_CHECK([for d_off in dirent], ac_cv_dirent_d_off,
[AC_TRY_COMPILE([
#include <unistd.h>
#include <sys/types.h>
#include <dirent.h>], [struct dirent d; d.d_off;],
ac_cv_dirent_d_off=yes, ac_cv_dirent_d_off=no)])
if test $ac_cv_dirent_d_off = yes; then
AC_DEFINE(HAVE_DIRENT_D_OFF,1,[Whether dirent has a d_off member])
fi
])
dnl AC_PROG_CC_FLAG(flag)
AC_DEFUN(AC_PROG_CC_FLAG,
[AC_CACHE_CHECK(whether ${CC-cc} accepts -$1, ac_cv_prog_cc_$1,
[echo 'void f(){}' > conftest.c
if test -z "`${CC-cc} -$1 -c conftest.c 2>&1`"; then
ac_cv_prog_cc_$1=yes
else
ac_cv_prog_cc_$1=no
fi
rm -f conftest*
])])
dnl see if a declaration exists for a function or variable
dnl defines HAVE_function_DECL if it exists
dnl AC_HAVE_DECL(var, includes)
AC_DEFUN(AC_HAVE_DECL,
[
AC_CACHE_CHECK([for $1 declaration],ac_cv_have_$1_decl,[
AC_TRY_COMPILE([$2],[int i = (int)$1],
ac_cv_have_$1_decl=yes,ac_cv_have_$1_decl=no)])
if test x"$ac_cv_have_$1_decl" = x"yes"; then
AC_DEFINE([HAVE_]translit([$1], [a-z], [A-Z])[_DECL],1,[Whether $1() is available])
fi
])
dnl check for a function in a library, but don't
dnl keep adding the same library to the LIBS variable.
dnl AC_LIBTESTFUNC(lib,func)
AC_DEFUN(AC_LIBTESTFUNC,
[case "$LIBS" in
*-l$1*) AC_CHECK_FUNCS($2) ;;
*) AC_CHECK_LIB($1, $2)
AC_CHECK_FUNCS($2)
;;
esac
])
dnl Define an AC_DEFINE with ifndef guard.
dnl AC_N_DEFINE(VARIABLE [, VALUE])
define(AC_N_DEFINE,
[cat >> confdefs.h <<\EOF
[#ifndef] $1
[#define] $1 ifelse($#, 2, [$2], $#, 3, [$2], 1)
[#endif]
EOF
])
dnl Add an #include
dnl AC_ADD_INCLUDE(VARIABLE)
define(AC_ADD_INCLUDE,
[cat >> confdefs.h <<\EOF
[#include] $1
EOF
])
dnl Copied from libtool.m4
AC_DEFUN(AC_PROG_LD_GNU,
[AC_CACHE_CHECK([if the linker ($LD) is GNU ld], ac_cv_prog_gnu_ld,
[# I'd rather use --version here, but apparently some GNU ld's only accept -v.
if $LD -v 2>&1 </dev/null | egrep '(GNU|with BFD)' 1>&5; then
ac_cv_prog_gnu_ld=yes
else
ac_cv_prog_gnu_ld=no
fi])
])
# Configure paths for LIBXML2
# Toshio Kuratomi 2001-04-21
# Adapted from:
# Configure paths for GLIB
# Owen Taylor 97-11-3
dnl AM_PATH_XML2([MINIMUM-VERSION, [ACTION-IF-FOUND [, ACTION-IF-NOT-FOUND]]])
dnl Test for XML, and define XML_CFLAGS and XML_LIBS
dnl
AC_DEFUN(AM_PATH_XML2,[
AC_ARG_WITH(xml-prefix,
[ --with-xml-prefix=PFX Prefix where libxml is installed (optional)],
xml_config_prefix="$withval", xml_config_prefix="")
AC_ARG_WITH(xml-exec-prefix,
[ --with-xml-exec-prefix=PFX Exec prefix where libxml is installed (optional)],
xml_config_exec_prefix="$withval", xml_config_exec_prefix="")
AC_ARG_ENABLE(xmltest,
[ --disable-xmltest Do not try to compile and run a test LIBXML program],,
enable_xmltest=yes)
if test x$xml_config_exec_prefix != x ; then
xml_config_args="$xml_config_args --exec-prefix=$xml_config_exec_prefix"
if test x${XML2_CONFIG+set} != xset ; then
XML2_CONFIG=$xml_config_exec_prefix/bin/xml2-config
fi
fi
if test x$xml_config_prefix != x ; then
xml_config_args="$xml_config_args --prefix=$xml_config_prefix"
if test x${XML2_CONFIG+set} != xset ; then
XML2_CONFIG=$xml_config_prefix/bin/xml2-config
fi
fi
AC_PATH_PROG(XML2_CONFIG, xml2-config, no)
min_xml_version=ifelse([$1], ,2.0.0,[$1])
AC_MSG_CHECKING(for libxml - version >= $min_xml_version)
no_xml=""
if test "$XML2_CONFIG" = "no" ; then
no_xml=yes
else
XML_CFLAGS=`$XML2_CONFIG $xml_config_args --cflags`
XML_LIBS=`$XML2_CONFIG $xml_config_args --libs`
xml_config_major_version=`$XML2_CONFIG $xml_config_args --version | \
sed 's/\([[0-9]]*\).\([[0-9]]*\).\([[0-9]]*\)/\1/'`
xml_config_minor_version=`$XML2_CONFIG $xml_config_args --version | \
sed 's/\([[0-9]]*\).\([[0-9]]*\).\([[0-9]]*\)/\2/'`
xml_config_micro_version=`$XML2_CONFIG $xml_config_args --version | \
sed 's/\([[0-9]]*\).\([[0-9]]*\).\([[0-9]]*\)/\3/'`
if test "x$enable_xmltest" = "xyes" ; then
ac_save_CFLAGS="$CFLAGS"
ac_save_LIBS="$LIBS"
CFLAGS="$CFLAGS $XML_CFLAGS"
LIBS="$XML_LIBS $LIBS"
dnl
dnl Now check if the installed libxml is sufficiently new.
dnl (Also sanity checks the results of xml2-config to some extent)
dnl
rm -f conf.xmltest
AC_TRY_RUN([
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <libxml/xmlversion.h>
int
main()
{
int xml_major_version, xml_minor_version, xml_micro_version;
int major, minor, micro;
char *tmp_version;
system("touch conf.xmltest");
/* Capture xml2-config output via autoconf/configure variables */
/* HP/UX 9 (%@#!) writes to sscanf strings */
tmp_version = (char *)strdup("$min_xml_version");
if (sscanf(tmp_version, "%d.%d.%d", &major, &minor, &micro) != 3) {
printf("%s, bad version string from xml2-config\n", "$min_xml_version");
exit(1);
}
free(tmp_version);
/* Capture the version information from the header files */
tmp_version = (char *)strdup(LIBXML_DOTTED_VERSION);
if (sscanf(tmp_version, "%d.%d.%d", &xml_major_version, &xml_minor_version, &xml_micro_version) != 3) {
printf("%s, bad version string from libxml includes\n", "LIBXML_DOTTED_VERSION");
exit(1);
}
free(tmp_version);
/* Compare xml2-config output to the libxml headers */
if ((xml_major_version != $xml_config_major_version) ||
(xml_minor_version != $xml_config_minor_version) ||
(xml_micro_version != $xml_config_micro_version))
{
printf("*** libxml header files (version %d.%d.%d) do not match\n",
xml_major_version, xml_minor_version, xml_micro_version);
printf("*** xml2-config (version %d.%d.%d)\n",
$xml_config_major_version, $xml_config_minor_version, $xml_config_micro_version);
return 1;
}
/* Compare the headers to the library to make sure we match */
/* Less than ideal -- doesn't provide us with return value feedback,
* only exits if there's a serious mismatch between header and library.
*/
LIBXML_TEST_VERSION;
/* Test that the library is greater than our minimum version */
if ((xml_major_version > major) ||
((xml_major_version == major) && (xml_minor_version > minor)) ||
((xml_major_version == major) && (xml_minor_version == minor) &&
(xml_micro_version >= micro)))
{
return 0;
}
else
{
printf("\n*** An old version of libxml (%d.%d.%d) was found.\n",
xml_major_version, xml_minor_version, xml_micro_version);
printf("*** You need a version of libxml newer than %d.%d.%d. The latest version of\n",
major, minor, micro);
printf("*** libxml is always available from ftp://ftp.xmlsoft.org.\n");
printf("***\n");
printf("*** If you have already installed a sufficiently new version, this error\n");
printf("*** probably means that the wrong copy of the xml2-config shell script is\n");
printf("*** being found. The easiest way to fix this is to remove the old version\n");
printf("*** of LIBXML, but you can also set the XML2_CONFIG environment to point to the\n");
printf("*** correct copy of xml2-config. (In this case, you will have to\n");
printf("*** modify your LD_LIBRARY_PATH enviroment variable, or edit /etc/ld.so.conf\n");
printf("*** so that the correct libraries are found at run-time))\n");
}
return 1;
}
],, no_xml=yes,[echo $ac_n "cross compiling; assumed OK... $ac_c"])
CFLAGS="$ac_save_CFLAGS"
LIBS="$ac_save_LIBS"
fi
fi
if test "x$no_xml" = x ; then
AC_MSG_RESULT(yes (version $xml_config_major_version.$xml_config_minor_version.$xml_config_micro_version))
ifelse([$2], , :, [$2])
else
AC_MSG_RESULT(no)
if test "$XML2_CONFIG" = "no" ; then
echo "*** The xml2-config script installed by LIBXML could not be found"
echo "*** If libxml was installed in PREFIX, make sure PREFIX/bin is in"
echo "*** your path, or set the XML2_CONFIG environment variable to the"
echo "*** full path to xml2-config."
else
if test -f conf.xmltest ; then
:
else
echo "*** Could not run libxml test program, checking why..."
CFLAGS="$CFLAGS $XML_CFLAGS"
LIBS="$LIBS $XML_LIBS"
AC_TRY_LINK([
#include <libxml/xmlversion.h>
#include <stdio.h>
], [ LIBXML_TEST_VERSION; return 0;],
[ echo "*** The test program compiled, but did not run. This usually means"
echo "*** that the run-time linker is not finding LIBXML or finding the wrong"
echo "*** version of LIBXML. If it is not finding LIBXML, you'll need to set your"
echo "*** LD_LIBRARY_PATH environment variable, or edit /etc/ld.so.conf to point"
echo "*** to the installed location Also, make sure you have run ldconfig if that"
echo "*** is required on your system"
echo "***"
echo "*** If you have an old version installed, it is best to remove it, although"
echo "*** you may also be able to get things to work by modifying LD_LIBRARY_PATH" ],
[ echo "*** The test program failed to compile or link. See the file config.log for the"
echo "*** exact error that occured. This usually means LIBXML was incorrectly installed"
echo "*** or that you have moved LIBXML since it was installed. In the latter case, you"
echo "*** may want to edit the xml2-config script: $XML2_CONFIG" ])
CFLAGS="$ac_save_CFLAGS"
LIBS="$ac_save_LIBS"
fi
fi
XML_CFLAGS=""
XML_LIBS=""
ifelse([$3], , :, [$3])
fi
AC_SUBST(XML_CFLAGS)
AC_SUBST(XML_LIBS)
rm -f conf.xmltest
])
# =========================================================================
# AM_PATH_MYSQL : MySQL library
dnl AM_PATH_MYSQL([MINIMUM-VERSION, [ACTION-IF-FOUND [, ACTION-IF-NOT-FOUND]]])
dnl Test for MYSQL, and define MYSQL_CFLAGS and MYSQL_LIBS
dnl
AC_DEFUN(AM_PATH_MYSQL,
[dnl
dnl Get the cflags and libraries from the mysql_config script
dnl
AC_ARG_WITH(mysql-prefix,[ --with-mysql-prefix=PFX Prefix where MYSQL is installed (optional)],
mysql_prefix="$withval", mysql_prefix="")
AC_ARG_WITH(mysql-exec-prefix,[ --with-mysql-exec-prefix=PFX Exec prefix where MYSQL is installed (optional)],
mysql_exec_prefix="$withval", mysql_exec_prefix="")
AC_ARG_ENABLE(mysqltest, [ --disable-mysqltest Do not try to compile and run a test MYSQL program],
, enable_mysqltest=yes)
if test x$mysql_exec_prefix != x ; then
mysql_args="$mysql_args --exec-prefix=$mysql_exec_prefix"
if test x${MYSQL_CONFIG+set} != xset ; then
MYSQL_CONFIG=$mysql_exec_prefix/bin/mysql_config
fi
fi
if test x$mysql_prefix != x ; then
mysql_args="$mysql_args --prefix=$mysql_prefix"
if test x${MYSQL_CONFIG+set} != xset ; then
MYSQL_CONFIG=$mysql_prefix/bin/mysql_config
fi
fi
AC_REQUIRE([AC_CANONICAL_TARGET])
AC_PATH_PROG(MYSQL_CONFIG, mysql_config, no)
min_mysql_version=ifelse([$1], ,0.11.0,$1)
AC_MSG_CHECKING(for MYSQL - version >= $min_mysql_version)
no_mysql=""
if test "$MYSQL_CONFIG" = "no" ; then
no_mysql=yes
else
MYSQL_CFLAGS=`$MYSQL_CONFIG $mysqlconf_args --cflags | sed -e "s/'//g"`
MYSQL_LIBS=`$MYSQL_CONFIG $mysqlconf_args --libs | sed -e "s/'//g"`
mysql_major_version=`$MYSQL_CONFIG $mysql_args --version | \
sed 's/\([[0-9]]*\).\([[0-9]]*\).\([[0-9]]*\)/\1/'`
mysql_minor_version=`$MYSQL_CONFIG $mysql_args --version | \
sed 's/\([[0-9]]*\).\([[0-9]]*\).\([[0-9]]*\)/\2/'`
mysql_micro_version=`$MYSQL_CONFIG $mysql_config_args --version | \
sed 's/\([[0-9]]*\).\([[0-9]]*\).\([[0-9]]*\)/\3/'`
if test "x$enable_mysqltest" = "xyes" ; then
ac_save_CFLAGS="$CFLAGS"
ac_save_LIBS="$LIBS"
CFLAGS="$CFLAGS $MYSQL_CFLAGS"
LIBS="$LIBS $MYSQL_LIBS"
dnl
dnl Now check if the installed MYSQL is sufficiently new. (Also sanity
dnl checks the results of mysql_config to some extent
dnl
rm -f conf.mysqltest
AC_TRY_RUN([
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <mysql.h>
char*
my_strdup (char *str)
{
char *new_str;
if (str)
{
new_str = (char *)malloc ((strlen (str) + 1) * sizeof(char));
strcpy (new_str, str);
}
else
new_str = NULL;
return new_str;
}
int main (int argc, char *argv[])
{
int major, minor, micro;
char *tmp_version;
/* This hangs on some systems (?)
system ("touch conf.mysqltest");
*/
{ FILE *fp = fopen("conf.mysqltest", "a"); if ( fp ) fclose(fp); }
/* HP/UX 9 (%@#!) writes to sscanf strings */
tmp_version = my_strdup("$min_mysql_version");
if (sscanf(tmp_version, "%d.%d.%d", &major, &minor, &micro) != 3) {
printf("%s, bad version string\n", "$min_mysql_version");
exit(1);
}
if (($mysql_major_version > major) ||
(($mysql_major_version == major) && ($mysql_minor_version > minor)) ||
(($mysql_major_version == major) && ($mysql_minor_version == minor) && ($mysql_micro_version >= micro)))
{
return 0;
}
else
{
printf("\n*** 'mysql_config --version' returned %d.%d.%d, but the minimum version\n", $mysql_major_version, $mysql_minor_version, $mysql_micro_version);
printf("*** of MYSQL required is %d.%d.%d. If mysql_config is correct, then it is\n", major, minor, micro);
printf("*** best to upgrade to the required version.\n");
printf("*** If mysql_config was wrong, set the environment variable MYSQL_CONFIG\n");
printf("*** to point to the correct copy of mysql_config, and remove the file\n");
printf("*** config.cache before re-running configure\n");
return 1;
}
}
],, no_mysql=yes,[echo $ac_n "cross compiling; assumed OK... $ac_c"])
CFLAGS="$ac_save_CFLAGS"
LIBS="$ac_save_LIBS"
fi
fi
if test "x$no_mysql" = x ; then
AC_MSG_RESULT(yes)
ifelse([$2], , :, [$2])
else
AC_MSG_RESULT(no)
if test "$MYSQL_CONFIG" = "no" ; then
echo "*** The mysql_config script installed by MYSQL could not be found"
echo "*** If MYSQL was installed in PREFIX, make sure PREFIX/bin is in"
echo "*** your path, or set the MYSQL_CONFIG environment variable to the"
echo "*** full path to mysql_config."
else
if test -f conf.mysqltest ; then
:
else
echo "*** Could not run MYSQL test program, checking why..."
CFLAGS="$CFLAGS $MYSQL_CFLAGS"
LIBS="$LIBS $MYSQL_LIBS"
AC_TRY_LINK([
#include <stdio.h>
#include <mysql.h>
int main(int argc, char *argv[])
{ return 0; }
#undef main
#define main K_and_R_C_main
], [ return 0; ],
[ echo "*** The test program compiled, but did not run. This usually means"
echo "*** that the run-time linker is not finding MYSQL or finding the wrong"
echo "*** version of MYSQL. If it is not finding MYSQL, you'll need to set your"
echo "*** LD_LIBRARY_PATH environment variable, or edit /etc/ld.so.conf to point"
echo "*** to the installed location Also, make sure you have run ldconfig if that"
echo "*** is required on your system"
echo "***"
echo "*** If you have an old version installed, it is best to remove it, although"
echo "*** you may also be able to get things to work by modifying LD_LIBRARY_PATH"],
[ echo "*** The test program failed to compile or link. See the file config.log for the"
echo "*** exact error that occured. This usually means MYSQL was incorrectly installed"
echo "*** or that you have moved MYSQL since it was installed. In the latter case, you"
echo "*** may want to edit the mysql_config script: $MYSQL_CONFIG" ])
CFLAGS="$ac_save_CFLAGS"
LIBS="$ac_save_LIBS"
fi
fi
MYSQL_CFLAGS=""
MYSQL_LIBS=""
ifelse([$3], , :, [$3])
fi
AC_SUBST(MYSQL_CFLAGS)
AC_SUBST(MYSQL_LIBS)
rm -f conf.mysqltest
])
dnl Removes -I/usr/include/? from given variable
AC_DEFUN(CFLAGS_REMOVE_USR_INCLUDE,[
ac_new_flags=""
for i in [$]$1; do
case [$]i in
-I/usr/include|-I/usr/include/) ;;
*) ac_new_flags="[$]ac_new_flags [$]i" ;;
esac
done
$1=[$]ac_new_flags
])
dnl Removes -L/usr/lib/? from given variable
AC_DEFUN(LIB_REMOVE_USR_LIB,[
ac_new_flags=""
for i in [$]$1; do
case [$]i in
-L/usr/lib|-L/usr/lib/) ;;
*) ac_new_flags="[$]ac_new_flags [$]i" ;;
esac
done
$1=[$]ac_new_flags
])
dnl From Bruno Haible.
AC_DEFUN(jm_ICONV,
[
dnl Some systems have iconv in libc, some have it in libiconv (OSF/1 and
dnl those with the standalone portable libiconv installed).
AC_MSG_CHECKING(for iconv in $1)
jm_cv_func_iconv="no"
jm_cv_lib_iconv=no
jm_cv_giconv=no
AC_TRY_LINK([#include <stdlib.h>
#include <giconv.h>],
[iconv_t cd = iconv_open("","");
iconv(cd,NULL,NULL,NULL,NULL);
iconv_close(cd);],
jm_cv_func_iconv=yes
jm_cv_giconv=yes)
if test "$jm_cv_func_iconv" != yes; then
AC_TRY_LINK([#include <stdlib.h>
#include <iconv.h>],
[iconv_t cd = iconv_open("","");
iconv(cd,NULL,NULL,NULL,NULL);
iconv_close(cd);],
jm_cv_func_iconv=yes)
if test "$jm_cv_lib_iconv" != yes; then
jm_save_LIBS="$LIBS"
LIBS="$LIBS -lgiconv"
AC_TRY_LINK([#include <stdlib.h>
#include <giconv.h>],
[iconv_t cd = iconv_open("","");
iconv(cd,NULL,NULL,NULL,NULL);
iconv_close(cd);],
jm_cv_lib_iconv=yes
jm_cv_func_iconv=yes
jm_cv_giconv=yes)
LIBS="$jm_save_LIBS"
if test "$jm_cv_func_iconv" != yes; then
jm_save_LIBS="$LIBS"
LIBS="$LIBS -liconv"
AC_TRY_LINK([#include <stdlib.h>
#include <iconv.h>],
[iconv_t cd = iconv_open("","");
iconv(cd,NULL,NULL,NULL,NULL);
iconv_close(cd);],
jm_cv_lib_iconv=yes
jm_cv_func_iconv=yes)
LIBS="$jm_save_LIBS"
fi
fi
fi
if test "$jm_cv_func_iconv" = yes; then
if test "$jm_cv_giconv" = yes; then
AC_DEFINE(HAVE_GICONV, 1, [What header to include for iconv() function: giconv.h])
AC_MSG_RESULT(yes)
ICONV_FOUND=yes
else
AC_DEFINE(HAVE_ICONV, 1, [What header to include for iconv() function: iconv.h])
AC_MSG_RESULT(yes)
ICONV_FOUND=yes
fi
else
AC_MSG_RESULT(no)
fi
if test "$jm_cv_lib_iconv" = yes; then
if test "$jm_cv_giconv" = yes; then
LIBS="$LIBS -lgiconv"
else
LIBS="$LIBS -liconv"
fi
fi
])
dnl CFLAGS_ADD_DIR(CFLAGS, $INCDIR)
dnl This function doesn't add -I/usr/include into CFLAGS
AC_DEFUN(CFLAGS_ADD_DIR,[
if test "$2" != "/usr/include" ; then
$1="$$1 -I$2"
fi
])
dnl LIB_ADD_DIR(LDFLAGS, $LIBDIR)
dnl This function doesn't add -L/usr/lib into LDFLAGS
AC_DEFUN(LIB_ADD_DIR,[
if test "$2" != "/usr/lib" ; then
$1="$$1 -L$2"
fi
])
dnl AC_ENABLE_SHARED - implement the --enable-shared flag
dnl Usage: AC_ENABLE_SHARED[(DEFAULT)]
dnl Where DEFAULT is either `yes' or `no'. If omitted, it defaults to
dnl `yes'.
AC_DEFUN([AC_ENABLE_SHARED],
[define([AC_ENABLE_SHARED_DEFAULT], ifelse($1, no, no, yes))dnl
AC_ARG_ENABLE(shared,
changequote(<<, >>)dnl
<< --enable-shared[=PKGS] build shared libraries [default=>>AC_ENABLE_SHARED_DEFAULT],
changequote([, ])dnl
[p=${PACKAGE-default}
case $enableval in
yes) enable_shared=yes ;;
no) enable_shared=no ;;
*)
enable_shared=no
# Look at the argument we got. We use all the common list separators.
IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:,"
for pkg in $enableval; do
if test "X$pkg" = "X$p"; then
enable_shared=yes
fi
done
IFS="$ac_save_ifs"
;;
esac],
enable_shared=AC_ENABLE_SHARED_DEFAULT)dnl
])
dnl AC_ENABLE_STATIC - implement the --enable-static flag
dnl Usage: AC_ENABLE_STATIC[(DEFAULT)]
dnl Where DEFAULT is either `yes' or `no'. If omitted, it defaults to
dnl `yes'.
AC_DEFUN([AC_ENABLE_STATIC],
[define([AC_ENABLE_STATIC_DEFAULT], ifelse($1, no, no, yes))dnl
AC_ARG_ENABLE(static,
changequote(<<, >>)dnl
<< --enable-static[=PKGS] build static libraries [default=>>AC_ENABLE_STATIC_DEFAULT],
changequote([, ])dnl
[p=${PACKAGE-default}
case $enableval in
yes) enable_static=yes ;;
no) enable_static=no ;;
*)
enable_static=no
# Look at the argument we got. We use all the common list separators.
IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:,"
for pkg in $enableval; do
if test "X$pkg" = "X$p"; then
enable_static=yes
fi
done
IFS="$ac_save_ifs"
;;
esac],
enable_static=AC_ENABLE_STATIC_DEFAULT)dnl
])
dnl AC_DISABLE_STATIC - set the default static flag to --disable-static
AC_DEFUN([AC_DISABLE_STATIC],
[AC_BEFORE([$0],[AC_LIBTOOL_SETUP])dnl
AC_ENABLE_STATIC(no)])

456
source4/auth/auth.c Normal file
View File

@ -0,0 +1,456 @@
/*
Unix SMB/CIFS implementation.
Password and authentication handling
Copyright (C) Andrew Bartlett 2001-2002
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "includes.h"
#undef DBGC_CLASS
#define DBGC_CLASS DBGC_AUTH
/** List of various built-in authentication modules */
static const struct auth_init_function_entry builtin_auth_init_functions[] = {
{ "guest", auth_init_guest },
// { "rhosts", auth_init_rhosts },
// { "hostsequiv", auth_init_hostsequiv },
{ "sam", auth_init_sam },
{ "samstrict", auth_init_samstrict },
{ "samstrict_dc", auth_init_samstrict_dc },
{ "unix", auth_init_unix },
// { "smbserver", auth_init_smbserver },
// { "ntdomain", auth_init_ntdomain },
// { "trustdomain", auth_init_trustdomain },
// { "winbind", auth_init_winbind },
#ifdef DEVELOPER
{ "name_to_ntstatus", auth_init_name_to_ntstatus },
{ "fixed_challenge", auth_init_fixed_challenge },
#endif
{ "plugin", auth_init_plugin },
{ NULL, NULL}
};
/****************************************************************************
Try to get a challenge out of the various authentication modules.
Returns a const char of length 8 bytes.
****************************************************************************/
static const uint8 *get_ntlm_challenge(struct auth_context *auth_context)
{
DATA_BLOB challenge = data_blob(NULL, 0);
const char *challenge_set_by = NULL;
auth_methods *auth_method;
TALLOC_CTX *mem_ctx;
if (auth_context->challenge.length) {
DEBUG(5, ("get_ntlm_challenge (auth subsystem): returning previous challenge by module %s (normal)\n",
auth_context->challenge_set_by));
return auth_context->challenge.data;
}
for (auth_method = auth_context->auth_method_list; auth_method; auth_method = auth_method->next) {
if (auth_method->get_chal == NULL) {
DEBUG(5, ("auth_get_challenge: module %s did not want to specify a challenge\n", auth_method->name));
continue;
}
DEBUG(5, ("auth_get_challenge: getting challenge from module %s\n", auth_method->name));
if (challenge_set_by != NULL) {
DEBUG(1, ("auth_get_challenge: CONFIGURATION ERROR: authentication method %s has already specified a challenge. Challenge by %s ignored.\n",
challenge_set_by, auth_method->name));
continue;
}
mem_ctx = talloc_init("auth_get_challenge for module %s", auth_method->name);
if (!mem_ctx) {
smb_panic("talloc_init() failed!");
}
challenge = auth_method->get_chal(auth_context, &auth_method->private_data, mem_ctx);
if (!challenge.length) {
DEBUG(3, ("auth_get_challenge: getting challenge from authentication method %s FAILED.\n",
auth_method->name));
} else {
DEBUG(5, ("auth_get_challenge: sucessfully got challenge from module %s\n", auth_method->name));
auth_context->challenge = challenge;
challenge_set_by = auth_method->name;
auth_context->challenge_set_method = auth_method;
}
talloc_destroy(mem_ctx);
}
if (!challenge_set_by) {
uchar chal[8];
generate_random_buffer(chal, sizeof(chal), False);
auth_context->challenge = data_blob_talloc(auth_context->mem_ctx,
chal, sizeof(chal));
challenge_set_by = "random";
}
DEBUG(5, ("auth_context challenge created by %s\n", challenge_set_by));
DEBUG(5, ("challenge is: \n"));
dump_data(5, auth_context->challenge.data, auth_context->challenge.length);
SMB_ASSERT(auth_context->challenge.length == 8);
auth_context->challenge_set_by=challenge_set_by;
return auth_context->challenge.data;
}
/**
* Check user is in correct domain (if required)
*
* @param user Only used to fill in the debug message
*
* @param domain The domain to be verified
*
* @return True if the user can connect with that domain,
* False otherwise.
**/
static BOOL check_domain_match(const char *user, const char *domain)
{
/*
* If we aren't serving to trusted domains, we must make sure that
* the validation request comes from an account in the same domain
* as the Samba server
*/
if (!lp_allow_trusted_domains() &&
!(strequal("", domain) ||
strequal(lp_workgroup(), domain) ||
is_myname(domain))) {
DEBUG(1, ("check_domain_match: Attempt to connect as user %s from domain %s denied.\n", user, domain));
return False;
} else {
return True;
}
}
/**
* Check a user's Plaintext, LM or NTLM password.
*
* Check a user's password, as given in the user_info struct and return various
* interesting details in the server_info struct.
*
* This function does NOT need to be in a become_root()/unbecome_root() pair
* as it makes the calls itself when needed.
*
* The return value takes precedence over the contents of the server_info
* struct. When the return is other than NT_STATUS_OK the contents
* of that structure is undefined.
*
* @param user_info Contains the user supplied components, including the passwords.
* Must be created with make_user_info() or one of its wrappers.
*
* @param auth_context Supplies the challenges and some other data.
* Must be created with make_auth_context(), and the challenges should be
* filled in, either at creation or by calling the challenge geneation
* function auth_get_challenge().
*
* @param server_info If successful, contains information about the authentication,
* including a SAM_ACCOUNT struct describing the user.
*
* @return An NTSTATUS with NT_STATUS_OK or an appropriate error.
*
**/
static NTSTATUS check_ntlm_password(const struct auth_context *auth_context,
const struct auth_usersupplied_info *user_info,
struct auth_serversupplied_info **server_info)
{
NTSTATUS nt_status = NT_STATUS_LOGON_FAILURE;
const char *pdb_username;
auth_methods *auth_method;
TALLOC_CTX *mem_ctx;
if (!user_info || !auth_context || !server_info)
return NT_STATUS_LOGON_FAILURE;
DEBUG(3, ("check_ntlm_password: Checking password for unmapped user [%s]\\[%s]@[%s] with the new password interface\n",
user_info->client_domain.str, user_info->smb_name.str, user_info->wksta_name.str));
DEBUG(3, ("check_ntlm_password: mapped user is: [%s]\\[%s]@[%s]\n",
user_info->domain.str, user_info->internal_username.str, user_info->wksta_name.str));
if (auth_context->challenge.length != 8) {
DEBUG(0, ("check_ntlm_password: Invalid challenge stored for this auth context - cannot continue\n"));
return NT_STATUS_LOGON_FAILURE;
}
if (auth_context->challenge_set_by)
DEBUG(10, ("check_ntlm_password: auth_context challenge created by %s\n",
auth_context->challenge_set_by));
DEBUG(10, ("challenge is: \n"));
dump_data(5, auth_context->challenge.data, auth_context->challenge.length);
#ifdef DEBUG_PASSWORD
DEBUG(100, ("user_info has passwords of length %d and %d\n",
user_info->lm_resp.length, user_info->nt_resp.length));
DEBUG(100, ("lm:\n"));
dump_data(100, user_info->lm_resp.data, user_info->lm_resp.length);
DEBUG(100, ("nt:\n"));
dump_data(100, user_info->nt_resp.data, user_info->nt_resp.length);
#endif
/* This needs to be sorted: If it doesn't match, what should we do? */
if (!check_domain_match(user_info->smb_name.str, user_info->domain.str))
return NT_STATUS_LOGON_FAILURE;
for (auth_method = auth_context->auth_method_list;auth_method; auth_method = auth_method->next) {
mem_ctx = talloc_init("%s authentication for user %s\\%s", auth_method->name,
user_info->domain.str, user_info->smb_name.str);
nt_status = auth_method->auth(auth_context, auth_method->private_data, mem_ctx, user_info, server_info);
if (NT_STATUS_IS_OK(nt_status)) {
DEBUG(3, ("check_ntlm_password: %s authentication for user [%s] suceeded\n",
auth_method->name, user_info->smb_name.str));
} else {
DEBUG(5, ("check_ntlm_password: %s authentication for user [%s] FAILED with error %s\n",
auth_method->name, user_info->smb_name.str, nt_errstr(nt_status)));
}
talloc_destroy(mem_ctx);
if (NT_STATUS_IS_OK(nt_status))
break;
}
/* This is one of the few places the *relies* (rather than just sets defaults
on the value of lp_security(). This needs to change. A new paramater
perhaps? */
if (lp_security() >= SEC_SERVER)
smb_user_control(user_info, *server_info, nt_status);
if (NT_STATUS_IS_OK(nt_status)) {
pdb_username = pdb_get_username((*server_info)->sam_account);
if (!(*server_info)->guest) {
/* We might not be root if we are an RPC call */
become_root();
nt_status = smb_pam_accountcheck(pdb_username);
unbecome_root();
if (NT_STATUS_IS_OK(nt_status)) {
DEBUG(5, ("check_ntlm_password: PAM Account for user [%s] suceeded\n",
pdb_username));
} else {
DEBUG(3, ("check_ntlm_password: PAM Account for user [%s] FAILED with error %s\n",
pdb_username, nt_errstr(nt_status)));
}
}
if (NT_STATUS_IS_OK(nt_status)) {
DEBUG((*server_info)->guest ? 5 : 2,
("check_ntlm_password: %sauthentication for user [%s] -> [%s] -> [%s] suceeded\n",
(*server_info)->guest ? "guest " : "",
user_info->smb_name.str,
user_info->internal_username.str,
pdb_username));
}
}
if (!NT_STATUS_IS_OK(nt_status)) {
DEBUG(2, ("check_ntlm_password: Authentication for user [%s] -> [%s] FAILED with error %s\n",
user_info->smb_name.str, user_info->internal_username.str,
nt_errstr(nt_status)));
ZERO_STRUCTP(server_info);
}
return nt_status;
}
/***************************************************************************
Clear out a auth_context, and destroy the attached TALLOC_CTX
***************************************************************************/
static void free_auth_context(struct auth_context **auth_context)
{
if (*auth_context != NULL)
talloc_destroy((*auth_context)->mem_ctx);
*auth_context = NULL;
}
/***************************************************************************
Make a auth_info struct
***************************************************************************/
static NTSTATUS make_auth_context(struct auth_context **auth_context)
{
TALLOC_CTX *mem_ctx;
mem_ctx = talloc_init("authentication context");
*auth_context = talloc(mem_ctx, sizeof(**auth_context));
if (!*auth_context) {
DEBUG(0,("make_auth_context: talloc failed!\n"));
talloc_destroy(mem_ctx);
return NT_STATUS_NO_MEMORY;
}
ZERO_STRUCTP(*auth_context);
(*auth_context)->mem_ctx = mem_ctx;
(*auth_context)->check_ntlm_password = check_ntlm_password;
(*auth_context)->get_ntlm_challenge = get_ntlm_challenge;
(*auth_context)->free = free_auth_context;
return NT_STATUS_OK;
}
/***************************************************************************
Make a auth_info struct for the auth subsystem
***************************************************************************/
static NTSTATUS make_auth_context_text_list(struct auth_context **auth_context, char **text_list)
{
auth_methods *list = NULL;
auth_methods *t = NULL;
auth_methods *tmp;
int i;
NTSTATUS nt_status;
if (!text_list) {
DEBUG(2,("make_auth_context_text_list: No auth method list!?\n"));
return NT_STATUS_UNSUCCESSFUL;
}
if (!NT_STATUS_IS_OK(nt_status = make_auth_context(auth_context)))
return nt_status;
for (;*text_list; text_list++) {
DEBUG(5,("make_auth_context_text_list: Attempting to find an auth method to match %s\n",
*text_list));
for (i = 0; builtin_auth_init_functions[i].name; i++) {
char *module_name = smb_xstrdup(*text_list);
char *module_params = NULL;
char *p;
p = strchr(module_name, ':');
if (p) {
*p = 0;
module_params = p+1;
trim_string(module_params, " ", " ");
}
trim_string(module_name, " ", " ");
if (strequal(builtin_auth_init_functions[i].name, module_name)) {
DEBUG(5,("make_auth_context_text_list: Found auth method %s (at pos %d)\n", *text_list, i));
if (NT_STATUS_IS_OK(builtin_auth_init_functions[i].init(*auth_context, module_params, &t))) {
DEBUG(5,("make_auth_context_text_list: auth method %s has a valid init\n",
*text_list));
DLIST_ADD_END(list, t, tmp);
} else {
DEBUG(0,("make_auth_context_text_list: auth method %s did not correctly init\n",
*text_list));
}
break;
}
SAFE_FREE(module_name);
}
}
(*auth_context)->auth_method_list = list;
return nt_status;
}
/***************************************************************************
Make a auth_context struct for the auth subsystem
***************************************************************************/
NTSTATUS make_auth_context_subsystem(struct auth_context **auth_context)
{
char **auth_method_list = NULL;
NTSTATUS nt_status;
if (lp_auth_methods() && !str_list_copy(&auth_method_list, lp_auth_methods())) {
return NT_STATUS_NO_MEMORY;
}
if (auth_method_list == NULL) {
switch (lp_security())
{
case SEC_DOMAIN:
DEBUG(5,("Making default auth method list for security=domain\n"));
auth_method_list = str_list_make("guest sam winbind ntdomain", NULL);
break;
case SEC_SERVER:
DEBUG(5,("Making default auth method list for security=server\n"));
auth_method_list = str_list_make("guest sam smbserver", NULL);
break;
case SEC_USER:
if (lp_encrypted_passwords()) {
DEBUG(5,("Making default auth method list for security=user, encrypt passwords = yes\n"));
auth_method_list = str_list_make("guest sam", NULL);
} else {
DEBUG(5,("Making default auth method list for security=user, encrypt passwords = no\n"));
auth_method_list = str_list_make("guest unix", NULL);
}
break;
case SEC_SHARE:
if (lp_encrypted_passwords()) {
DEBUG(5,("Making default auth method list for security=share, encrypt passwords = yes\n"));
auth_method_list = str_list_make("guest sam", NULL);
} else {
DEBUG(5,("Making default auth method list for security=share, encrypt passwords = no\n"));
auth_method_list = str_list_make("guest unix", NULL);
}
break;
case SEC_ADS:
DEBUG(5,("Making default auth method list for security=ADS\n"));
auth_method_list = str_list_make("guest sam ads winbind ntdomain", NULL);
break;
default:
DEBUG(5,("Unknown auth method!\n"));
return NT_STATUS_UNSUCCESSFUL;
}
} else {
DEBUG(5,("Using specified auth order\n"));
}
if (!NT_STATUS_IS_OK(nt_status = make_auth_context_text_list(auth_context, auth_method_list))) {
str_list_free(&auth_method_list);
return nt_status;
}
str_list_free(&auth_method_list);
return nt_status;
}
/***************************************************************************
Make a auth_info struct with a fixed challenge
***************************************************************************/
NTSTATUS make_auth_context_fixed(struct auth_context **auth_context, uchar chal[8])
{
NTSTATUS nt_status;
if (!NT_STATUS_IS_OK(nt_status = make_auth_context_subsystem(auth_context))) {
return nt_status;
}
(*auth_context)->challenge = data_blob(chal, 8);
(*auth_context)->challenge_set_by = "fixed";
return nt_status;
}

210
source4/auth/auth_builtin.c Normal file
View File

@ -0,0 +1,210 @@
/*
Unix SMB/CIFS implementation.
Generic authenticaion types
Copyright (C) Andrew Bartlett 2001-2002
Copyright (C) Jelmer Vernooij 2002
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "includes.h"
#undef DBGC_CLASS
#define DBGC_CLASS DBGC_AUTH
/**
* Return a guest logon for guest users (username = "")
*
* Typically used as the first module in the auth chain, this allows
* guest logons to be dealt with in one place. Non-guest logons 'fail'
* and pass onto the next module.
**/
static NTSTATUS check_guest_security(const struct auth_context *auth_context,
void *my_private_data,
TALLOC_CTX *mem_ctx,
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
NTSTATUS nt_status = NT_STATUS_LOGON_FAILURE;
if (!(user_info->internal_username.str
&& *user_info->internal_username.str)) {
nt_status = make_server_info_guest(server_info);
}
return nt_status;
}
/* Guest modules initialisation */
NTSTATUS auth_init_guest(struct auth_context *auth_context, const char *options, auth_methods **auth_method)
{
if (!make_auth_methods(auth_context, auth_method))
return NT_STATUS_NO_MEMORY;
(*auth_method)->auth = check_guest_security;
(*auth_method)->name = "guest";
return NT_STATUS_OK;
}
/**
* Return an error based on username
*
* This function allows the testing of obsure errors, as well as the generation
* of NT_STATUS -> DOS error mapping tables.
*
* This module is of no value to end-users.
*
* The password is ignored.
*
* @return An NTSTATUS value based on the username
**/
static NTSTATUS check_name_to_ntstatus_security(const struct auth_context *auth_context,
void *my_private_data,
TALLOC_CTX *mem_ctx,
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
NTSTATUS nt_status;
fstring user;
long error_num;
fstrcpy(user, user_info->smb_name.str);
if (strncasecmp("NT_STATUS", user, strlen("NT_STATUS")) == 0) {
strupper(user);
return nt_status_string_to_code(user);
}
strlower(user);
error_num = strtoul(user, NULL, 16);
DEBUG(5,("check_name_to_ntstatus_security: Error for user %s was %lx\n", user, error_num));
nt_status = NT_STATUS(error_num);
return nt_status;
}
/** Module initailisation function */
NTSTATUS auth_init_name_to_ntstatus(struct auth_context *auth_context, const char *param, auth_methods **auth_method)
{
if (!make_auth_methods(auth_context, auth_method))
return NT_STATUS_NO_MEMORY;
(*auth_method)->auth = check_name_to_ntstatus_security;
(*auth_method)->name = "name_to_ntstatus";
return NT_STATUS_OK;
}
/**
* Return a 'fixed' challenge instead of a varaible one.
*
* The idea of this function is to make packet snifs consistant
* with a fixed challenge, so as to aid debugging.
*
* This module is of no value to end-users.
*
* This module does not actually authenticate the user, but
* just pretenteds to need a specified challenge.
* This module removes *all* security from the challenge-response system
*
* @return NT_STATUS_UNSUCCESSFUL
**/
static NTSTATUS check_fixed_challenge_security(const struct auth_context *auth_context,
void *my_private_data,
TALLOC_CTX *mem_ctx,
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
return NT_STATUS_UNSUCCESSFUL;
}
/****************************************************************************
Get the challenge out of a password server.
****************************************************************************/
static DATA_BLOB auth_get_fixed_challenge(const struct auth_context *auth_context,
void **my_private_data,
TALLOC_CTX *mem_ctx)
{
const char *challenge = "I am a teapot";
return data_blob(challenge, 8);
}
/** Module initailisation function */
NTSTATUS auth_init_fixed_challenge(struct auth_context *auth_context, const char *param, auth_methods **auth_method)
{
if (!make_auth_methods(auth_context, auth_method))
return NT_STATUS_NO_MEMORY;
(*auth_method)->auth = check_fixed_challenge_security;
(*auth_method)->get_chal = auth_get_fixed_challenge;
(*auth_method)->name = "fixed_challenge";
return NT_STATUS_OK;
}
/**
* Outsorce an auth module to an external loadable .so
*
* Only works on systems with dlopen() etc.
**/
/* Plugin modules initialisation */
NTSTATUS auth_init_plugin(struct auth_context *auth_context, const char *param, auth_methods **auth_method)
{
void * dl_handle;
char *plugin_param, *plugin_name, *p;
auth_init_function plugin_init;
if (param == NULL) {
DEBUG(0, ("auth_init_plugin: The plugin module needs an argument!\n"));
return NT_STATUS_UNSUCCESSFUL;
}
plugin_name = smb_xstrdup(param);
p = strchr(plugin_name, ':');
if (p) {
*p = 0;
plugin_param = p+1;
trim_string(plugin_param, " ", " ");
} else plugin_param = NULL;
trim_string(plugin_name, " ", " ");
DEBUG(5, ("auth_init_plugin: Trying to load auth plugin %s\n", plugin_name));
dl_handle = sys_dlopen(plugin_name, RTLD_NOW );
if (!dl_handle) {
DEBUG(0, ("auth_init_plugin: Failed to load auth plugin %s using sys_dlopen (%s)\n",
plugin_name, sys_dlerror()));
return NT_STATUS_UNSUCCESSFUL;
}
plugin_init = sys_dlsym(dl_handle, "auth_init");
if (!plugin_init){
DEBUG(0, ("Failed to find function 'auth_init' using sys_dlsym in sam plugin %s (%s)\n",
plugin_name, sys_dlerror()));
return NT_STATUS_UNSUCCESSFUL;
}
DEBUG(5, ("Starting sam plugin %s with paramater %s\n", plugin_name, plugin_param?plugin_param:"(null)"));
return plugin_init(auth_context, plugin_param, auth_method);
}

122
source4/auth/auth_compat.c Normal file
View File

@ -0,0 +1,122 @@
/*
Unix SMB/CIFS implementation.
Password and authentication handling
Copyright (C) Andrew Bartlett 2001-2002
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "includes.h"
#undef DBGC_CLASS
#define DBGC_CLASS DBGC_AUTH
/****************************************************************************
COMPATIBILITY INTERFACES:
***************************************************************************/
/****************************************************************************
check if a username/password is OK assuming the password is a 24 byte
SMB hash
return True if the password is correct, False otherwise
****************************************************************************/
NTSTATUS check_plaintext_password(const char *smb_name, DATA_BLOB plaintext_password, auth_serversupplied_info **server_info)
{
struct auth_context *plaintext_auth_context = NULL;
auth_usersupplied_info *user_info = NULL;
const uint8 *chal;
NTSTATUS nt_status;
if (!NT_STATUS_IS_OK(nt_status = make_auth_context_subsystem(&plaintext_auth_context))) {
return nt_status;
}
chal = plaintext_auth_context->get_ntlm_challenge(plaintext_auth_context);
if (!make_user_info_for_reply(&user_info,
smb_name, lp_workgroup(), chal,
plaintext_password)) {
return NT_STATUS_NO_MEMORY;
}
nt_status = plaintext_auth_context->check_ntlm_password(plaintext_auth_context,
user_info, server_info);
(plaintext_auth_context->free)(&plaintext_auth_context);
free_user_info(&user_info);
return nt_status;
}
static NTSTATUS pass_check_smb(struct server_context *smb,
const char *smb_name,
const char *domain,
DATA_BLOB lm_pwd,
DATA_BLOB nt_pwd,
DATA_BLOB plaintext_password,
BOOL encrypted)
{
NTSTATUS nt_status;
auth_serversupplied_info *server_info = NULL;
if (encrypted) {
auth_usersupplied_info *user_info = NULL;
make_user_info_for_reply_enc(&user_info, smb_name,
domain,
lm_pwd,
nt_pwd);
nt_status = smb->negotiate.auth_context->check_ntlm_password(smb->negotiate.auth_context,
user_info, &server_info);
free_user_info(&user_info);
} else {
nt_status = check_plaintext_password(smb_name, plaintext_password, &server_info);
}
free_server_info(&server_info);
return nt_status;
}
/****************************************************************************
check if a username/password pair is ok via the auth subsystem.
return True if the password is correct, False otherwise
****************************************************************************/
BOOL password_ok(struct server_context *smb, const char *smb_name, DATA_BLOB password_blob)
{
DATA_BLOB null_password = data_blob(NULL, 0);
BOOL encrypted = (smb->negotiate.encrypted_passwords && password_blob.length == 24);
NTSTATUS status;
if (encrypted) {
/*
* The password could be either NTLM or plain LM. Try NTLM first,
* but fall-through as required.
* NTLMv2 makes no sense here.
*/
status = pass_check_smb(smb, smb_name, lp_workgroup(), null_password,
password_blob, null_password, encrypted);
if (NT_STATUS_IS_OK(status)) {
return True;
}
status = pass_check_smb(smb, smb_name, lp_workgroup(), password_blob,
null_password, null_password, encrypted);
} else {
status = pass_check_smb(smb, smb_name, lp_workgroup(), null_password,
null_password, password_blob, encrypted);
}
return NT_STATUS_IS_OK(status);
}

554
source4/auth/auth_domain.c Normal file
View File

@ -0,0 +1,554 @@
/*
Unix SMB/CIFS implementation.
Authenticate against a remote domain
Copyright (C) Andrew Tridgell 1992-1998
Copyright (C) Andrew Bartlett 2001
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "includes.h"
#undef DBGC_CLASS
#define DBGC_CLASS DBGC_AUTH
BOOL global_machine_password_needs_changing = False;
extern userdom_struct current_user_info;
/*
resolve the name of a DC in ways appropriate for an ADS domain mode
an ADS domain may not have Netbios enabled at all, so this is
quite different from the RPC case
Note that we ignore the 'server' parameter here. That has the effect of using
the 'ADS server' smb.conf parameter, which is what we really want anyway
*/
static NTSTATUS ads_resolve_dc(fstring remote_machine,
struct in_addr *dest_ip)
{
ADS_STRUCT *ads;
ads = ads_init_simple();
if (!ads) {
return NT_STATUS_NO_LOGON_SERVERS;
}
DEBUG(4,("ads_resolve_dc: realm=%s\n", ads->config.realm));
ads->auth.flags |= ADS_AUTH_NO_BIND;
#ifdef HAVE_ADS
/* a full ads_connect() is actually overkill, as we don't srictly need
to do the SASL auth in order to get the info we need, but libads
doesn't offer a better way right now */
ads_connect(ads);
#endif
fstrcpy(remote_machine, ads->config.ldap_server_name);
strupper(remote_machine);
*dest_ip = ads->ldap_ip;
ads_destroy(&ads);
if (!*remote_machine || is_zero_ip(*dest_ip)) {
return NT_STATUS_NO_LOGON_SERVERS;
}
DEBUG(4,("ads_resolve_dc: using server='%s' IP=%s\n",
remote_machine, inet_ntoa(*dest_ip)));
return NT_STATUS_OK;
}
/*
resolve the name of a DC in ways appropriate for RPC domain mode
this relies on the server supporting netbios and port 137 not being
firewalled
*/
static NTSTATUS rpc_resolve_dc(const char *server,
fstring remote_machine,
struct in_addr *dest_ip)
{
if (is_ipaddress(server)) {
struct in_addr to_ip = *interpret_addr2(server);
/* we need to know the machines netbios name - this is a lousy
way to find it, but until we have a RPC call that does this
it will have to do */
if (!name_status_find("*", 0x20, 0x20, to_ip, remote_machine)) {
DEBUG(2, ("rpc_resolve_dc: Can't resolve name for IP %s\n", server));
return NT_STATUS_NO_LOGON_SERVERS;
}
*dest_ip = to_ip;
return NT_STATUS_OK;
}
fstrcpy(remote_machine, server);
strupper(remote_machine);
if (!resolve_name(remote_machine, dest_ip, 0x20)) {
DEBUG(1,("rpc_resolve_dc: Can't resolve address for %s\n",
remote_machine));
return NT_STATUS_NO_LOGON_SERVERS;
}
DEBUG(4,("rpc_resolve_dc: using server='%s' IP=%s\n",
remote_machine, inet_ntoa(*dest_ip)));
return NT_STATUS_OK;
}
/**
* Connect to a remote server for domain security authenticaion.
*
* @param cli the cli to return containing the active connection
* @param server either a machine name or text IP address to
* connect to.
* @param trust_passwd the trust password to establish the
* credentials with.
*
**/
static NTSTATUS connect_to_domain_password_server(struct cli_state **cli,
const char *server,
const char *setup_creds_as,
uint16 sec_chan,
const unsigned char *trust_passwd,
BOOL *retry)
{
struct in_addr dest_ip;
fstring remote_machine;
NTSTATUS result;
uint32 neg_flags = 0x000001ff;
*retry = False;
if (lp_security() == SEC_ADS)
result = ads_resolve_dc(remote_machine, &dest_ip);
else
result = rpc_resolve_dc(server, remote_machine, &dest_ip);
if (!NT_STATUS_IS_OK(result)) {
DEBUG(2,("connect_to_domain_password_server: unable to resolve DC: %s\n",
nt_errstr(result)));
return result;
}
if (ismyip(dest_ip)) {
DEBUG(1,("connect_to_domain_password_server: Password server loop - not using password server %s\n",
remote_machine));
return NT_STATUS_NO_LOGON_SERVERS;
}
/* TODO: Send a SAMLOGON request to determine whether this is a valid
logonserver. We can avoid a 30-second timeout if the DC is down
if the SAMLOGON request fails as it is only over UDP. */
/* we use a mutex to prevent two connections at once - when a
Win2k PDC get two connections where one hasn't completed a
session setup yet it will send a TCP reset to the first
connection (tridge) */
/*
* With NT4.x DC's *all* authentication must be serialized to avoid
* ACCESS_DENIED errors if 2 auths are done from the same machine. JRA.
*/
*retry = True;
if (!grab_server_mutex(server))
return NT_STATUS_NO_LOGON_SERVERS;
/* Attempt connection */
result = cli_full_connection(cli, lp_netbios_name(), remote_machine,
&dest_ip, 0, "IPC$", "IPC", "", "", "",0, retry);
if (!NT_STATUS_IS_OK(result)) {
release_server_mutex();
return result;
}
/*
* We now have an anonymous connection to IPC$ on the domain password server.
*/
/*
* Even if the connect succeeds we need to setup the netlogon
* pipe here. We do this as we may just have changed the domain
* account password on the PDC and yet we may be talking to
* a BDC that doesn't have this replicated yet. In this case
* a successful connect to a DC needs to take the netlogon connect
* into account also. This patch from "Bjart Kvarme" <bjart.kvarme@usit.uio.no>.
*/
if(cli_nt_session_open(*cli, PI_NETLOGON) == False) {
DEBUG(0,("connect_to_domain_password_server: unable to open the domain client session to \
machine %s. Error was : %s.\n", remote_machine, cli_errstr(*cli)));
cli_nt_session_close(*cli);
cli_ulogoff(*cli);
cli_shutdown(*cli);
release_server_mutex();
return NT_STATUS_NO_LOGON_SERVERS;
}
snprintf((*cli)->mach_acct, sizeof((*cli)->mach_acct) - 1, "%s$", setup_creds_as);
if (!(*cli)->mach_acct) {
release_server_mutex();
return NT_STATUS_NO_MEMORY;
}
result = cli_nt_setup_creds(*cli, sec_chan, trust_passwd, &neg_flags, 2);
if (!NT_STATUS_IS_OK(result)) {
DEBUG(0,("connect_to_domain_password_server: unable to setup the NETLOGON credentials to machine \
%s. Error was : %s.\n", remote_machine, nt_errstr(result)));
cli_nt_session_close(*cli);
cli_ulogoff(*cli);
cli_shutdown(*cli);
release_server_mutex();
return result;
}
/* We exit here with the mutex *locked*. JRA */
return NT_STATUS_OK;
}
/***********************************************************************
Utility function to attempt a connection to an IP address of a DC.
************************************************************************/
static NTSTATUS attempt_connect_to_dc(struct cli_state **cli,
const char *domain,
struct in_addr *ip,
const char *setup_creds_as,
uint16 sec_chan,
const unsigned char *trust_passwd)
{
NTSTATUS ret = NT_STATUS_UNSUCCESSFUL;
BOOL retry = True;
fstring dc_name;
int i;
/*
* Ignore addresses we have already tried.
*/
if (is_zero_ip(*ip))
return NT_STATUS_NO_LOGON_SERVERS;
if (!lookup_dc_name(lp_netbios_name(), domain, ip, dc_name))
return NT_STATUS_NO_LOGON_SERVERS;
for (i = 0; (!NT_STATUS_IS_OK(ret)) && retry && (i < 3); i++)
ret = connect_to_domain_password_server(cli, dc_name, setup_creds_as,
sec_chan, trust_passwd, &retry);
return ret;
}
/***********************************************************************
We have been asked to dynamically determine the IP addresses of
the PDC and BDC's for DOMAIN, and query them in turn.
************************************************************************/
static NTSTATUS find_connect_dc(struct cli_state **cli,
const char *domain,
const char *setup_creds_as,
uint16 sec_chan,
unsigned char *trust_passwd,
time_t last_change_time)
{
struct in_addr dc_ip;
fstring srv_name;
if ( !rpc_find_dc(lp_workgroup(), srv_name, &dc_ip) ) {
DEBUG(0,("find_connect_dc: Failed to find an DCs for %s\n", lp_workgroup()));
return NT_STATUS_NO_LOGON_SERVERS;
}
return attempt_connect_to_dc( cli, domain, &dc_ip, setup_creds_as,
sec_chan, trust_passwd );
}
/***********************************************************************
Do the same as security=server, but using NT Domain calls and a session
key from the machine password. If the server parameter is specified
use it, otherwise figure out a server from the 'password server' param.
************************************************************************/
static NTSTATUS domain_client_validate(TALLOC_CTX *mem_ctx,
const auth_usersupplied_info *user_info,
const char *domain,
uchar chal[8],
auth_serversupplied_info **server_info,
const char *server, const char *setup_creds_as,
uint16 sec_chan,
unsigned char trust_passwd[16],
time_t last_change_time)
{
fstring remote_machine;
NET_USER_INFO_3 info3;
struct cli_state *cli = NULL;
NTSTATUS nt_status = NT_STATUS_NO_LOGON_SERVERS;
/*
* At this point, smb_apasswd points to the lanman response to
* the challenge in local_challenge, and smb_ntpasswd points to
* the NT response to the challenge in local_challenge. Ship
* these over the secure channel to a domain controller and
* see if they were valid.
*/
while (!NT_STATUS_IS_OK(nt_status) &&
next_token(&server,remote_machine,LIST_SEP,sizeof(remote_machine))) {
if(lp_security() != SEC_ADS && strequal(remote_machine, "*")) {
nt_status = find_connect_dc(&cli, domain, setup_creds_as, sec_chan, trust_passwd, last_change_time);
} else {
int i;
BOOL retry = True;
for (i = 0; !NT_STATUS_IS_OK(nt_status) && retry && (i < 3); i++)
nt_status = connect_to_domain_password_server(&cli, remote_machine, setup_creds_as,
sec_chan, trust_passwd, &retry);
}
}
if (!NT_STATUS_IS_OK(nt_status)) {
DEBUG(0,("domain_client_validate: Domain password server not available.\n"));
return nt_status;
}
ZERO_STRUCT(info3);
/*
* If this call succeeds, we now have lots of info about the user
* in the info3 structure.
*/
nt_status = cli_netlogon_sam_network_logon(cli, mem_ctx,
user_info->smb_name.str, user_info->domain.str,
user_info->wksta_name.str, chal,
user_info->lm_resp, user_info->nt_resp,
&info3);
if (!NT_STATUS_IS_OK(nt_status)) {
DEBUG(0,("domain_client_validate: unable to validate password "
"for user %s in domain %s to Domain controller %s. "
"Error was %s.\n", user_info->smb_name.str,
user_info->domain.str, cli->srv_name_slash,
nt_errstr(nt_status)));
} else {
nt_status = make_server_info_info3(mem_ctx, user_info->internal_username.str,
user_info->smb_name.str, domain, server_info, &info3);
#if 0
/* The stuff doesn't work right yet */
SMB_ASSERT(sizeof((*server_info)->session_key) == sizeof(info3.user_sess_key));
memcpy((*server_info)->session_key, info3.user_sess_key, sizeof((*server_info)->session_key)/* 16 */);
SamOEMhash((*server_info)->session_key, trust_passwd, sizeof((*server_info)->session_key));
#endif
uni_group_cache_store_netlogon(mem_ctx, &info3);
}
#if 0
/*
* We don't actually need to do this - plus it fails currently with
* NT_STATUS_INVALID_INFO_CLASS - we need to know *exactly* what to
* send here. JRA.
*/
if (NT_STATUS_IS_OK(status)) {
if(cli_nt_logoff(&cli, &ctr) == False) {
DEBUG(0,("domain_client_validate: unable to log off user %s in domain \
%s to Domain controller %s. Error was %s.\n", user, domain, remote_machine, cli_errstr(&cli)));
nt_status = NT_STATUS_LOGON_FAILURE;
}
}
#endif /* 0 */
/* Note - once the cli stream is shutdown the mem_ctx used
to allocate the other_sids and gids structures has been deleted - so
these pointers are no longer valid..... */
cli_nt_session_close(cli);
cli_ulogoff(cli);
cli_shutdown(cli);
release_server_mutex();
return nt_status;
}
/****************************************************************************
Check for a valid username and password in security=domain mode.
****************************************************************************/
static NTSTATUS check_ntdomain_security(const struct auth_context *auth_context,
void *my_private_data,
TALLOC_CTX *mem_ctx,
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
NTSTATUS nt_status = NT_STATUS_LOGON_FAILURE;
char *password_server;
unsigned char trust_passwd[16];
time_t last_change_time;
const char *domain = lp_workgroup();
if (!user_info || !server_info || !auth_context) {
DEBUG(1,("check_ntdomain_security: Critical variables not present. Failing.\n"));
return NT_STATUS_INVALID_PARAMETER;
}
/*
* Check that the requested domain is not our own machine name.
* If it is, we should never check the PDC here, we use our own local
* password file.
*/
if(is_myname(user_info->domain.str)) {
DEBUG(3,("check_ntdomain_security: Requested domain was for this machine.\n"));
return NT_STATUS_LOGON_FAILURE;
}
/*
* Get the machine account password for our primary domain
* No need to become_root() as secrets_init() is done at startup.
*/
if (!secrets_fetch_trust_account_password(domain, trust_passwd, &last_change_time))
{
DEBUG(0, ("check_ntdomain_security: could not fetch trust account password for domain '%s'\n", domain));
return NT_STATUS_CANT_ACCESS_DOMAIN_INFO;
}
/* Test if machine password has expired and needs to be changed */
if (lp_machine_password_timeout()) {
if (last_change_time > 0 &&
time(NULL) > (last_change_time +
lp_machine_password_timeout())) {
global_machine_password_needs_changing = True;
}
}
/*
* Treat each name in the 'password server =' line as a potential
* PDC/BDC. Contact each in turn and try and authenticate.
*/
password_server = lp_passwordserver();
nt_status = domain_client_validate(mem_ctx, user_info, domain,
(uchar *)auth_context->challenge.data,
server_info,
password_server, lp_netbios_name(), SEC_CHAN_WKSTA, trust_passwd, last_change_time);
return nt_status;
}
/* module initialisation */
NTSTATUS auth_init_ntdomain(struct auth_context *auth_context, const char* param, auth_methods **auth_method)
{
if (!make_auth_methods(auth_context, auth_method)) {
return NT_STATUS_NO_MEMORY;
}
(*auth_method)->name = "ntdomain";
(*auth_method)->auth = check_ntdomain_security;
return NT_STATUS_OK;
}
/****************************************************************************
Check for a valid username and password in a trusted domain
****************************************************************************/
static NTSTATUS check_trustdomain_security(const struct auth_context *auth_context,
void *my_private_data,
TALLOC_CTX *mem_ctx,
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
NTSTATUS nt_status = NT_STATUS_LOGON_FAILURE;
unsigned char trust_md4_password[16];
char *trust_password;
time_t last_change_time;
DOM_SID sid;
if (!user_info || !server_info || !auth_context) {
DEBUG(1,("check_trustdomain_security: Critical variables not present. Failing.\n"));
return NT_STATUS_INVALID_PARAMETER;
}
/*
* Check that the requested domain is not our own machine name.
* If it is, we should never check the PDC here, we use our own local
* password file.
*/
if(is_myname(user_info->domain.str)) {
DEBUG(3,("check_trustdomain_security: Requested domain was for this machine.\n"));
return NT_STATUS_LOGON_FAILURE;
}
/*
* Check that the requested domain is not our own domain,
* If it is, we should use our own local password file.
*/
if(strequal(lp_workgroup(), (user_info->domain.str))) {
DEBUG(3,("check_trustdomain_security: Requested domain was for this domain.\n"));
return NT_STATUS_LOGON_FAILURE;
}
/*
* Get the trusted account password for the trusted domain
* No need to become_root() as secrets_init() is done at startup.
*/
if (!secrets_fetch_trusted_domain_password(user_info->domain.str, &trust_password, &sid, &last_change_time))
{
DEBUG(0, ("check_trustdomain_security: could not fetch trust account password for domain %s\n", user_info->domain.str));
return NT_STATUS_CANT_ACCESS_DOMAIN_INFO;
}
#ifdef DEBUG_PASSWORD
DEBUG(100, ("Trust password for domain %s is %s\n", user_info->domain.str, trust_password));
#endif
E_md4hash(trust_password, trust_md4_password);
SAFE_FREE(trust_password);
#if 0
/* Test if machine password is expired and need to be changed */
if (time(NULL) > last_change_time + lp_machine_password_timeout())
{
global_machine_password_needs_changing = True;
}
#endif
nt_status = domain_client_validate(mem_ctx, user_info, user_info->domain.str,
(uchar *)auth_context->challenge.data,
server_info, "*" /* Do a lookup */,
lp_workgroup(), SEC_CHAN_DOMAIN, trust_md4_password, last_change_time);
return nt_status;
}
/* module initialisation */
NTSTATUS auth_init_trustdomain(struct auth_context *auth_context, const char* param, auth_methods **auth_method)
{
if (!make_auth_methods(auth_context, auth_method)) {
return NT_STATUS_NO_MEMORY;
}
(*auth_method)->name = "trustdomain";
(*auth_method)->auth = check_trustdomain_security;
return NT_STATUS_OK;
}

138
source4/auth/auth_ntlmssp.c Normal file
View File

@ -0,0 +1,138 @@
/*
Unix SMB/Netbios implementation.
Version 3.0
handle NLTMSSP, server side
Copyright (C) Andrew Tridgell 2001
Copyright (C) Andrew Bartlett 2001-2003
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "includes.h"
static const uint8 *auth_ntlmssp_get_challenge(struct ntlmssp_state *ntlmssp_state)
{
AUTH_NTLMSSP_STATE *auth_ntlmssp_state = ntlmssp_state->auth_context;
return auth_ntlmssp_state->auth_context->get_ntlm_challenge(auth_ntlmssp_state->auth_context);
}
static NTSTATUS auth_ntlmssp_check_password(struct ntlmssp_state *ntlmssp_state)
{
AUTH_NTLMSSP_STATE *auth_ntlmssp_state = ntlmssp_state->auth_context;
uint32 auth_flags = AUTH_FLAG_NONE;
auth_usersupplied_info *user_info = NULL;
DATA_BLOB plaintext_password = data_blob(NULL, 0);
NTSTATUS nt_status;
if (auth_ntlmssp_state->ntlmssp_state->lm_resp.length) {
auth_flags |= AUTH_FLAG_LM_RESP;
}
if (auth_ntlmssp_state->ntlmssp_state->nt_resp.length == 24) {
auth_flags |= AUTH_FLAG_NTLM_RESP;
} else if (auth_ntlmssp_state->ntlmssp_state->nt_resp.length > 24) {
auth_flags |= AUTH_FLAG_NTLMv2_RESP;
};
/* the client has given us its machine name (which we otherwise would not get on port 445).
we need to possibly reload smb.conf if smb.conf includes depend on the machine name */
sub_set_remote_machine(auth_ntlmssp_state->ntlmssp_state->workstation);
/* setup the string used by %U */
/* sub_set_smb_name checks for weird internally */
sub_set_user_name(auth_ntlmssp_state->ntlmssp_state->user);
reload_services(True);
nt_status = make_user_info_map(&user_info,
auth_ntlmssp_state->ntlmssp_state->user,
auth_ntlmssp_state->ntlmssp_state->domain,
auth_ntlmssp_state->ntlmssp_state->workstation,
auth_ntlmssp_state->ntlmssp_state->lm_resp,
auth_ntlmssp_state->ntlmssp_state->nt_resp,
plaintext_password,
auth_flags, True);
if (!NT_STATUS_IS_OK(nt_status)) {
return nt_status;
}
nt_status = auth_ntlmssp_state->auth_context->check_ntlm_password(auth_ntlmssp_state->auth_context, user_info, &auth_ntlmssp_state->server_info);
free_user_info(&user_info);
return nt_status;
}
NTSTATUS auth_ntlmssp_start(AUTH_NTLMSSP_STATE **auth_ntlmssp_state)
{
NTSTATUS nt_status;
TALLOC_CTX *mem_ctx;
mem_ctx = talloc_init("AUTH NTLMSSP context");
*auth_ntlmssp_state = talloc_zero(mem_ctx, sizeof(**auth_ntlmssp_state));
if (!*auth_ntlmssp_state) {
DEBUG(0,("auth_ntlmssp_start: talloc failed!\n"));
talloc_destroy(mem_ctx);
return NT_STATUS_NO_MEMORY;
}
ZERO_STRUCTP(*auth_ntlmssp_state);
(*auth_ntlmssp_state)->mem_ctx = mem_ctx;
if (!NT_STATUS_IS_OK(nt_status = ntlmssp_server_start(&(*auth_ntlmssp_state)->ntlmssp_state))) {
return nt_status;
}
if (!NT_STATUS_IS_OK(nt_status = make_auth_context_subsystem(&(*auth_ntlmssp_state)->auth_context))) {
return nt_status;
}
(*auth_ntlmssp_state)->ntlmssp_state->auth_context = (*auth_ntlmssp_state);
(*auth_ntlmssp_state)->ntlmssp_state->get_challenge = auth_ntlmssp_get_challenge;
(*auth_ntlmssp_state)->ntlmssp_state->check_password = auth_ntlmssp_check_password;
(*auth_ntlmssp_state)->ntlmssp_state->server_role = lp_server_role();
return NT_STATUS_OK;
}
NTSTATUS auth_ntlmssp_end(AUTH_NTLMSSP_STATE **auth_ntlmssp_state)
{
TALLOC_CTX *mem_ctx = (*auth_ntlmssp_state)->mem_ctx;
if ((*auth_ntlmssp_state)->ntlmssp_state) {
ntlmssp_server_end(&(*auth_ntlmssp_state)->ntlmssp_state);
}
if ((*auth_ntlmssp_state)->auth_context) {
((*auth_ntlmssp_state)->auth_context->free)(&(*auth_ntlmssp_state)->auth_context);
}
if ((*auth_ntlmssp_state)->server_info) {
free_server_info(&(*auth_ntlmssp_state)->server_info);
}
talloc_destroy(mem_ctx);
*auth_ntlmssp_state = NULL;
return NT_STATUS_OK;
}
NTSTATUS auth_ntlmssp_update(AUTH_NTLMSSP_STATE *auth_ntlmssp_state,
const DATA_BLOB request, DATA_BLOB *reply)
{
return ntlmssp_server_update(auth_ntlmssp_state->ntlmssp_state, request, reply);
}

564
source4/auth/auth_sam.c Normal file
View File

@ -0,0 +1,564 @@
/*
Unix SMB/CIFS implementation.
Password and authentication handling
Copyright (C) Andrew Tridgell 1992-2000
Copyright (C) Luke Kenneth Casson Leighton 1996-2000
Copyright (C) Andrew Bartlett 2001
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "includes.h"
#undef DBGC_CLASS
#define DBGC_CLASS DBGC_AUTH
/****************************************************************************
core of smb password checking routine.
****************************************************************************/
static BOOL smb_pwd_check_ntlmv1(DATA_BLOB nt_response,
const uchar *part_passwd,
DATA_BLOB sec_blob,
uint8 user_sess_key[16])
{
/* Finish the encryption of part_passwd. */
uchar p24[24];
if (part_passwd == NULL) {
DEBUG(10,("No password set - DISALLOWING access\n"));
/* No password set - always false ! */
return False;
}
if (sec_blob.length != 8) {
DEBUG(0, ("smb_pwd_check_ntlmv1: incorrect challenge size (%d)\n", sec_blob.length));
return False;
}
if (nt_response.length != 24) {
DEBUG(0, ("smb_pwd_check_ntlmv1: incorrect password length (%d)\n", nt_response.length));
return False;
}
SMBOWFencrypt(part_passwd, sec_blob.data, p24);
if (user_sess_key != NULL)
{
SMBsesskeygen_ntv1(part_passwd, NULL, user_sess_key);
}
#if DEBUG_PASSWORD
DEBUG(100,("Part password (P16) was |"));
dump_data(100, part_passwd, 16);
DEBUG(100,("Password from client was |"));
dump_data(100, nt_response.data, nt_response.length);
DEBUG(100,("Given challenge was |"));
dump_data(100, sec_blob.data, sec_blob.length);
DEBUG(100,("Value from encryption was |"));
dump_data(100, p24, 24);
#endif
return (memcmp(p24, nt_response.data, 24) == 0);
}
/****************************************************************************
core of smb password checking routine. (NTLMv2, LMv2)
Note: The same code works with both NTLMv2 and LMv2.
****************************************************************************/
static BOOL smb_pwd_check_ntlmv2(const DATA_BLOB ntv2_response,
const uchar *part_passwd,
const DATA_BLOB sec_blob,
const char *user, const char *domain,
uint8 user_sess_key[16])
{
/* Finish the encryption of part_passwd. */
uchar kr[16];
uchar value_from_encryption[16];
uchar client_response[16];
DATA_BLOB client_key_data;
if (part_passwd == NULL)
{
DEBUG(10,("No password set - DISALLOWING access\n"));
/* No password set - always False */
return False;
}
if (ntv2_response.length < 16) {
/* We MUST have more than 16 bytes, or the stuff below will go
crazy... */
DEBUG(0, ("smb_pwd_check_ntlmv2: incorrect password length (%d)\n",
ntv2_response.length));
return False;
}
client_key_data = data_blob(ntv2_response.data+16, ntv2_response.length-16);
/*
todo: should we be checking this for anything? We can't for LMv2,
but for NTLMv2 it is meant to contain the current time etc.
*/
memcpy(client_response, ntv2_response.data, sizeof(client_response));
if (!ntv2_owf_gen(part_passwd, user, domain, kr)) {
return False;
}
SMBOWFencrypt_ntv2(kr, sec_blob, client_key_data, value_from_encryption);
if (user_sess_key != NULL)
{
SMBsesskeygen_ntv2(kr, value_from_encryption, user_sess_key);
}
#if DEBUG_PASSWORD
DEBUG(100,("Part password (P16) was |"));
dump_data(100, part_passwd, 16);
DEBUG(100,("Password from client was |"));
dump_data(100, ntv2_response.data, ntv2_response.length);
DEBUG(100,("Variable data from client was |"));
dump_data(100, client_key_data.data, client_key_data.length);
DEBUG(100,("Given challenge was |"));
dump_data(100, sec_blob.data, sec_blob.length);
DEBUG(100,("Value from encryption was |"));
dump_data(100, value_from_encryption, 16);
#endif
data_blob_clear_free(&client_key_data);
return (memcmp(value_from_encryption, client_response, 16) == 0);
}
/****************************************************************************
Do a specific test for an smb password being correct, given a smb_password and
the lanman and NT responses.
****************************************************************************/
static NTSTATUS sam_password_ok(const struct auth_context *auth_context,
TALLOC_CTX *mem_ctx,
SAM_ACCOUNT *sampass,
const auth_usersupplied_info *user_info,
uint8 user_sess_key[16])
{
uint16 acct_ctrl;
const uint8 *nt_pw, *lm_pw;
uint32 auth_flags;
acct_ctrl = pdb_get_acct_ctrl(sampass);
if (acct_ctrl & ACB_PWNOTREQ)
{
if (lp_null_passwords())
{
DEBUG(3,("Account for user '%s' has no password and null passwords are allowed.\n", pdb_get_username(sampass)));
return(NT_STATUS_OK);
}
else
{
DEBUG(3,("Account for user '%s' has no password and null passwords are NOT allowed.\n", pdb_get_username(sampass)));
return(NT_STATUS_LOGON_FAILURE);
}
}
auth_flags = user_info->auth_flags;
if (IS_SAM_DEFAULT(sampass, PDB_NTPASSWD)) {
DEBUG(3,("sam_password_ok: NO NT password stored for user %s.\n",
pdb_get_username(sampass)));
/* No return, we want to check the LM hash below in this case */
auth_flags &= (~(AUTH_FLAG_NTLMv2_RESP | AUTH_FLAG_NTLM_RESP));
}
if (auth_flags & AUTH_FLAG_NTLMv2_RESP) {
nt_pw = pdb_get_nt_passwd(sampass);
/* We have the NT MD4 hash challenge available - see if we can
use it (ie. does it exist in the smbpasswd file).
*/
DEBUG(4,("sam_password_ok: Checking NTLMv2 password with domain [%s]\n", user_info->client_domain.str));
if (smb_pwd_check_ntlmv2( user_info->nt_resp,
nt_pw, auth_context->challenge,
user_info->smb_name.str,
user_info->client_domain.str,
user_sess_key))
{
return NT_STATUS_OK;
}
DEBUG(4,("sam_password_ok: Checking NTLMv2 password without a domain\n"));
if (smb_pwd_check_ntlmv2( user_info->nt_resp,
nt_pw, auth_context->challenge,
user_info->smb_name.str,
"",
user_sess_key))
{
return NT_STATUS_OK;
} else {
DEBUG(3,("sam_password_ok: NTLMv2 password check failed\n"));
return NT_STATUS_WRONG_PASSWORD;
}
} else if (auth_flags & AUTH_FLAG_NTLM_RESP) {
if (lp_ntlm_auth()) {
nt_pw = pdb_get_nt_passwd(sampass);
/* We have the NT MD4 hash challenge available - see if we can
use it (ie. does it exist in the smbpasswd file).
*/
DEBUG(4,("sam_password_ok: Checking NT MD4 password\n"));
if (smb_pwd_check_ntlmv1(user_info->nt_resp,
nt_pw, auth_context->challenge,
user_sess_key))
{
return NT_STATUS_OK;
} else {
DEBUG(3,("sam_password_ok: NT MD4 password check failed for user %s\n",pdb_get_username(sampass)));
return NT_STATUS_WRONG_PASSWORD;
}
} else {
DEBUG(2,("sam_password_ok: NTLMv1 passwords NOT PERMITTED for user %s\n",pdb_get_username(sampass)));
/* no return, becouse we might pick up LMv2 in the LM feild */
}
}
if (auth_flags & AUTH_FLAG_LM_RESP) {
if (user_info->lm_resp.length != 24) {
DEBUG(2,("sam_password_ok: invalid LanMan password length (%d) for user %s\n",
user_info->nt_resp.length, pdb_get_username(sampass)));
}
if (!lp_lanman_auth()) {
DEBUG(3,("sam_password_ok: Lanman passwords NOT PERMITTED for user %s\n",pdb_get_username(sampass)));
} else if (IS_SAM_DEFAULT(sampass, PDB_LMPASSWD)) {
DEBUG(3,("sam_password_ok: NO LanMan password set for user %s (and no NT password supplied)\n",pdb_get_username(sampass)));
} else {
lm_pw = pdb_get_lanman_passwd(sampass);
DEBUG(4,("sam_password_ok: Checking LM password\n"));
if (smb_pwd_check_ntlmv1(user_info->lm_resp,
lm_pw, auth_context->challenge,
user_sess_key))
{
return NT_STATUS_OK;
}
}
if (IS_SAM_DEFAULT(sampass, PDB_NTPASSWD)) {
DEBUG(4,("sam_password_ok: LM password check failed for user, no NT password %s\n",pdb_get_username(sampass)));
return NT_STATUS_WRONG_PASSWORD;
}
nt_pw = pdb_get_nt_passwd(sampass);
/* This is for 'LMv2' authentication. almost NTLMv2 but limited to 24 bytes.
- related to Win9X, legacy NAS pass-though authentication
*/
DEBUG(4,("sam_password_ok: Checking LMv2 password with domain %s\n", user_info->client_domain.str));
if (smb_pwd_check_ntlmv2( user_info->lm_resp,
nt_pw, auth_context->challenge,
user_info->smb_name.str,
user_info->client_domain.str,
user_sess_key))
{
return NT_STATUS_OK;
}
DEBUG(4,("sam_password_ok: Checking LMv2 password without a domain\n"));
if (smb_pwd_check_ntlmv2( user_info->lm_resp,
nt_pw, auth_context->challenge,
user_info->smb_name.str,
"",
user_sess_key))
{
return NT_STATUS_OK;
}
/* Apparently NT accepts NT responses in the LM field
- I think this is related to Win9X pass-though authentication
*/
DEBUG(4,("sam_password_ok: Checking NT MD4 password in LM field\n"));
if (lp_ntlm_auth())
{
if (smb_pwd_check_ntlmv1(user_info->lm_resp,
nt_pw, auth_context->challenge,
user_sess_key))
{
return NT_STATUS_OK;
}
DEBUG(3,("sam_password_ok: LM password, NT MD4 password in LM field and LMv2 failed for user %s\n",pdb_get_username(sampass)));
return NT_STATUS_WRONG_PASSWORD;
} else {
DEBUG(3,("sam_password_ok: LM password and LMv2 failed for user %s, and NT MD4 password in LM field not permitted\n",pdb_get_username(sampass)));
return NT_STATUS_WRONG_PASSWORD;
}
}
/* Should not be reached, but if they send nothing... */
DEBUG(3,("sam_password_ok: NEITHER LanMan nor NT password supplied for user %s\n",pdb_get_username(sampass)));
return NT_STATUS_WRONG_PASSWORD;
}
/****************************************************************************
Do a specific test for a SAM_ACCOUNT being vaild for this connection
(ie not disabled, expired and the like).
****************************************************************************/
static NTSTATUS sam_account_ok(TALLOC_CTX *mem_ctx,
SAM_ACCOUNT *sampass,
const auth_usersupplied_info *user_info)
{
uint16 acct_ctrl = pdb_get_acct_ctrl(sampass);
char *workstation_list;
time_t kickoff_time;
DEBUG(4,("sam_account_ok: Checking SMB password for user %s\n",pdb_get_username(sampass)));
/* Quit if the account was disabled. */
if (acct_ctrl & ACB_DISABLED) {
DEBUG(1,("Account for user '%s' was disabled.\n", pdb_get_username(sampass)));
return NT_STATUS_ACCOUNT_DISABLED;
}
/* Test account expire time */
kickoff_time = pdb_get_kickoff_time(sampass);
if (kickoff_time != 0 && time(NULL) > kickoff_time) {
DEBUG(1,("Account for user '%s' has expried.\n", pdb_get_username(sampass)));
DEBUG(3,("Account expired at '%ld' unix time.\n", (long)kickoff_time));
return NT_STATUS_ACCOUNT_EXPIRED;
}
if (!(pdb_get_acct_ctrl(sampass) & ACB_PWNOEXP)) {
time_t must_change_time = pdb_get_pass_must_change_time(sampass);
time_t last_set_time = pdb_get_pass_last_set_time(sampass);
/* check for immediate expiry "must change at next logon" */
if (must_change_time == 0 && last_set_time != 0) {
DEBUG(1,("Account for user '%s' password must change!.\n", pdb_get_username(sampass)));
return NT_STATUS_PASSWORD_MUST_CHANGE;
}
/* check for expired password */
if (must_change_time < time(NULL) && must_change_time != 0) {
DEBUG(1,("Account for user '%s' password expired!.\n", pdb_get_username(sampass)));
DEBUG(1,("Password expired at '%s' (%ld) unix time.\n", http_timestring(mem_ctx, must_change_time), (long)must_change_time));
return NT_STATUS_PASSWORD_EXPIRED;
}
}
/* Test workstation. Workstation list is comma separated. */
workstation_list = talloc_strdup(mem_ctx, pdb_get_workstations(sampass));
if (!workstation_list) return NT_STATUS_NO_MEMORY;
if (*workstation_list) {
BOOL invalid_ws = True;
const char *s = workstation_list;
fstring tok;
while (next_token(&s, tok, ",", sizeof(tok))) {
DEBUG(10,("checking for workstation match %s and %s (len=%d)\n",
tok, user_info->wksta_name.str, user_info->wksta_name.len));
if(strequal(tok, user_info->wksta_name.str)) {
invalid_ws = False;
break;
}
}
if (invalid_ws)
return NT_STATUS_INVALID_WORKSTATION;
}
if (acct_ctrl & ACB_DOMTRUST) {
DEBUG(2,("sam_account_ok: Domain trust account %s denied by server\n", pdb_get_username(sampass)));
return NT_STATUS_NOLOGON_INTERDOMAIN_TRUST_ACCOUNT;
}
if (acct_ctrl & ACB_SVRTRUST) {
DEBUG(2,("sam_account_ok: Server trust account %s denied by server\n", pdb_get_username(sampass)));
return NT_STATUS_NOLOGON_SERVER_TRUST_ACCOUNT;
}
if (acct_ctrl & ACB_WSTRUST) {
DEBUG(4,("sam_account_ok: Wksta trust account %s denied by server\n", pdb_get_username(sampass)));
return NT_STATUS_NOLOGON_WORKSTATION_TRUST_ACCOUNT;
}
return NT_STATUS_OK;
}
/****************************************************************************
check if a username/password is OK assuming the password is a 24 byte
SMB hash supplied in the user_info structure
return an NT_STATUS constant.
****************************************************************************/
static NTSTATUS check_sam_security(const struct auth_context *auth_context,
void *my_private_data,
TALLOC_CTX *mem_ctx,
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
SAM_ACCOUNT *sampass=NULL;
BOOL ret;
NTSTATUS nt_status;
uint8 user_sess_key[16];
const uint8* lm_hash;
if (!user_info || !auth_context) {
return NT_STATUS_UNSUCCESSFUL;
}
/* Can't use the talloc version here, becouse the returned struct gets
kept on the server_info */
if (!NT_STATUS_IS_OK(nt_status = pdb_init_sam(&sampass))) {
return nt_status;
}
/* get the account information */
become_root();
ret = pdb_getsampwnam(sampass, user_info->internal_username.str);
unbecome_root();
if (ret == False)
{
DEBUG(3,("Couldn't find user '%s' in passdb file.\n", user_info->internal_username.str));
pdb_free_sam(&sampass);
return NT_STATUS_NO_SUCH_USER;
}
nt_status = sam_account_ok(mem_ctx, sampass, user_info);
if (!NT_STATUS_IS_OK(nt_status)) {
pdb_free_sam(&sampass);
return nt_status;
}
nt_status = sam_password_ok(auth_context, mem_ctx, sampass, user_info, user_sess_key);
if (!NT_STATUS_IS_OK(nt_status)) {
pdb_free_sam(&sampass);
return nt_status;
}
if (!NT_STATUS_IS_OK(nt_status = make_server_info_sam(server_info, sampass))) {
DEBUG(0,("check_sam_security: make_server_info_sam() failed with '%s'\n", nt_errstr(nt_status)));
return nt_status;
}
lm_hash = pdb_get_lanman_passwd((*server_info)->sam_account);
if (lm_hash) {
memcpy((*server_info)->first_8_lm_hash, lm_hash, 8);
}
memcpy((*server_info)->session_key, user_sess_key, sizeof(user_sess_key));
return nt_status;
}
/* module initialisation */
NTSTATUS auth_init_sam(struct auth_context *auth_context, const char *param, auth_methods **auth_method)
{
if (!make_auth_methods(auth_context, auth_method)) {
return NT_STATUS_NO_MEMORY;
}
(*auth_method)->auth = check_sam_security;
(*auth_method)->name = "sam";
return NT_STATUS_OK;
}
/****************************************************************************
Check SAM security (above) but with a few extra checks.
****************************************************************************/
static NTSTATUS check_samstrict_security(const struct auth_context *auth_context,
void *my_private_data,
TALLOC_CTX *mem_ctx,
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
if (!user_info || !auth_context) {
return NT_STATUS_LOGON_FAILURE;
}
/* If we are a domain member, we must not
attempt to check the password locally,
unless it is one of our aliases. */
if (!is_myname(user_info->domain.str)) {
DEBUG(7,("The requested user domain is not the local server name. [%s]\\[%s]\n",
user_info->domain.str,user_info->internal_username.str));
return NT_STATUS_NO_SUCH_USER;
}
return check_sam_security(auth_context, my_private_data, mem_ctx, user_info, server_info);
}
/* module initialisation */
NTSTATUS auth_init_samstrict(struct auth_context *auth_context, const char *param, auth_methods **auth_method)
{
if (!make_auth_methods(auth_context, auth_method)) {
return NT_STATUS_NO_MEMORY;
}
(*auth_method)->auth = check_samstrict_security;
(*auth_method)->name = "samstrict";
return NT_STATUS_OK;
}
/****************************************************************************
Check SAM security (above) but with a few extra checks if we're a DC.
****************************************************************************/
static NTSTATUS check_samstrict_dc_security(const struct auth_context *auth_context,
void *my_private_data,
TALLOC_CTX *mem_ctx,
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
if (!user_info || !auth_context) {
return NT_STATUS_LOGON_FAILURE;
}
/* If we are a domain member, we must not
attempt to check the password locally,
unless it is one of our aliases, empty
or our domain if we are a logon server.*/
if ((strcasecmp(lp_workgroup(), user_info->domain.str) != 0) &&
(!is_myname(user_info->domain.str))) {
DEBUG(7,("The requested user domain is not the local server name or our domain. [%s]\\[%s]\n",
user_info->domain.str,user_info->internal_username.str));
return NT_STATUS_NO_SUCH_USER;
}
return check_sam_security(auth_context, my_private_data, mem_ctx, user_info, server_info);
}
/* module initialisation */
NTSTATUS auth_init_samstrict_dc(struct auth_context *auth_context, const char *param, auth_methods **auth_method)
{
if (!make_auth_methods(auth_context, auth_method)) {
return NT_STATUS_NO_MEMORY;
}
(*auth_method)->auth = check_samstrict_dc_security;
(*auth_method)->name = "samstrict_dc";
return NT_STATUS_OK;
}

402
source4/auth/auth_server.c Normal file
View File

@ -0,0 +1,402 @@
/*
Unix SMB/CIFS implementation.
Authenticate to a remote server
Copyright (C) Andrew Tridgell 1992-1998
Copyright (C) Andrew Bartlett 2001
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "includes.h"
#undef DBGC_CLASS
#define DBGC_CLASS DBGC_AUTH
extern userdom_struct current_user_info;
/****************************************************************************
Support for server level security.
****************************************************************************/
static struct cli_state *server_cryptkey(TALLOC_CTX *mem_ctx)
{
struct cli_state *cli = NULL;
fstring desthost;
struct in_addr dest_ip;
const char *p;
char *pserver;
BOOL connected_ok = False;
if (!(cli = cli_initialise(cli)))
return NULL;
/* security = server just can't function with spnego */
cli->use_spnego = False;
pserver = talloc_strdup(mem_ctx, lp_passwordserver());
p = pserver;
while(next_token( &p, desthost, LIST_SEP, sizeof(desthost))) {
standard_sub_basic(current_user_info.smb_name, desthost, sizeof(desthost));
strupper(desthost);
if(!resolve_name( desthost, &dest_ip, 0x20)) {
DEBUG(1,("server_cryptkey: Can't resolve address for %s\n",desthost));
continue;
}
if (ismyip(dest_ip)) {
DEBUG(1,("Password server loop - disabling password server %s\n",desthost));
continue;
}
/* we use a mutex to prevent two connections at once - when a
Win2k PDC get two connections where one hasn't completed a
session setup yet it will send a TCP reset to the first
connection (tridge) */
if (!grab_server_mutex(desthost)) {
return NULL;
}
if (cli_connect(cli, desthost, &dest_ip)) {
DEBUG(3,("connected to password server %s\n",desthost));
connected_ok = True;
break;
}
}
if (!connected_ok) {
release_server_mutex();
DEBUG(0,("password server not available\n"));
cli_shutdown(cli);
return NULL;
}
if (!attempt_netbios_session_request(cli, lp_netbios_name(),
desthost, &dest_ip)) {
release_server_mutex();
DEBUG(1,("password server fails session request\n"));
cli_shutdown(cli);
return NULL;
}
if (strequal(desthost,myhostname(mem_ctx))) {
exit_server("Password server loop!");
}
DEBUG(3,("got session\n"));
if (!cli_negprot(cli)) {
DEBUG(1,("%s rejected the negprot\n",desthost));
release_server_mutex();
cli_shutdown(cli);
return NULL;
}
if (cli->protocol < PROTOCOL_LANMAN2 ||
!(cli->sec_mode & NEGOTIATE_SECURITY_USER_LEVEL)) {
DEBUG(1,("%s isn't in user level security mode\n",desthost));
release_server_mutex();
cli_shutdown(cli);
return NULL;
}
/* Get the first session setup done quickly, to avoid silly
Win2k bugs. (The next connection to the server will kill
this one...
*/
if (!cli_session_setup(cli, "", "", 0, "", 0,
"")) {
DEBUG(0,("%s rejected the initial session setup (%s)\n",
desthost, cli_errstr(cli)));
release_server_mutex();
cli_shutdown(cli);
return NULL;
}
release_server_mutex();
DEBUG(3,("password server OK\n"));
return cli;
}
/****************************************************************************
Clean up our allocated cli.
****************************************************************************/
static void free_server_private_data(void **private_data_pointer)
{
struct cli_state **cli = (struct cli_state **)private_data_pointer;
if (*cli && (*cli)->initialised) {
cli_shutdown(*cli);
}
}
/****************************************************************************
Send a 'keepalive' packet down the cli pipe.
****************************************************************************/
static void send_server_keepalive(void **private_data_pointer)
{
struct cli_state **cli = (struct cli_state **)private_data_pointer;
/* also send a keepalive to the password server if its still
connected */
if (cli && *cli && (*cli)->initialised) {
if (!send_nbt_keepalive((*cli)->fd)) {
DEBUG( 2, ( "password server keepalive failed.\n"));
cli_shutdown(*cli);
}
}
}
/****************************************************************************
Get the challenge out of a password server.
****************************************************************************/
static DATA_BLOB auth_get_challenge_server(const struct auth_context *auth_context,
void **my_private_data,
TALLOC_CTX *mem_ctx)
{
struct cli_state *cli = server_cryptkey(mem_ctx);
if (cli) {
DEBUG(3,("using password server validation\n"));
if ((cli->sec_mode & NEGOTIATE_SECURITY_CHALLENGE_RESPONSE) == 0) {
/* We can't work with unencrypted password servers
unless 'encrypt passwords = no' */
DEBUG(5,("make_auth_info_server: Server is unencrypted, no challenge available..\n"));
/* However, it is still a perfectly fine connection
to pass that unencrypted password over */
*my_private_data = (void *)cli;
return data_blob(NULL, 0);
} else if (cli->secblob.length < 8) {
/* We can't do much if we don't get a full challenge */
DEBUG(2,("make_auth_info_server: Didn't receive a full challenge from server\n"));
cli_shutdown(cli);
return data_blob(NULL, 0);
}
*my_private_data = (void *)cli;
/* The return must be allocated on the caller's mem_ctx, as our own will be
destoyed just after the call. */
return data_blob_talloc(auth_context->mem_ctx, cli->secblob.data,8);
} else {
return data_blob(NULL, 0);
}
}
/****************************************************************************
Check for a valid username and password in security=server mode.
- Validate a password with the password server.
****************************************************************************/
static NTSTATUS check_smbserver_security(const struct auth_context *auth_context,
void *my_private_data,
TALLOC_CTX *mem_ctx,
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
struct cli_state *cli;
static unsigned char badpass[24];
static fstring baduser;
static BOOL tested_password_server = False;
static BOOL bad_password_server = False;
NTSTATUS nt_status = NT_STATUS_LOGON_FAILURE;
BOOL locally_made_cli = False;
/*
* Check that the requested domain is not our own machine name.
* If it is, we should never check the PDC here, we use our own local
* password file.
*/
if(is_myname(user_info->domain.str)) {
DEBUG(3,("check_smbserver_security: Requested domain was for this machine.\n"));
return NT_STATUS_LOGON_FAILURE;
}
cli = my_private_data;
if (cli) {
} else {
cli = server_cryptkey(mem_ctx);
locally_made_cli = True;
}
if (!cli || !cli->initialised) {
DEBUG(1,("password server is not connected (cli not initilised)\n"));
return NT_STATUS_LOGON_FAILURE;
}
if ((cli->sec_mode & NEGOTIATE_SECURITY_CHALLENGE_RESPONSE) == 0) {
if (user_info->encrypted) {
DEBUG(1,("password server %s is plaintext, but we are encrypted. This just can't work :-(\n", cli->desthost));
return NT_STATUS_LOGON_FAILURE;
}
} else {
if (memcmp(cli->secblob.data, auth_context->challenge.data, 8) != 0) {
DEBUG(1,("the challenge that the password server (%s) supplied us is not the one we gave our client. This just can't work :-(\n", cli->desthost));
return NT_STATUS_LOGON_FAILURE;
}
}
if(badpass[0] == 0)
memset(badpass, 0x1f, sizeof(badpass));
if((user_info->nt_resp.length == sizeof(badpass)) &&
!memcmp(badpass, user_info->nt_resp.data, sizeof(badpass))) {
/*
* Very unlikely, our random bad password is the same as the users
* password.
*/
memset(badpass, badpass[0]+1, sizeof(badpass));
}
if(baduser[0] == 0) {
fstrcpy(baduser, INVALID_USER_PREFIX);
fstrcat(baduser, lp_netbios_name());
}
/*
* Attempt a session setup with a totally incorrect password.
* If this succeeds with the guest bit *NOT* set then the password
* server is broken and is not correctly setting the guest bit. We
* need to detect this as some versions of NT4.x are broken. JRA.
*/
/* I sure as hell hope that there aren't servers out there that take
* NTLMv2 and have this bug, as we don't test for that...
* - abartlet@samba.org
*/
if ((!tested_password_server) && (lp_paranoid_server_security())) {
if (cli_session_setup(cli, baduser, (char *)badpass, sizeof(badpass),
(char *)badpass, sizeof(badpass), user_info->domain.str)) {
/*
* We connected to the password server so we
* can say we've tested it.
*/
tested_password_server = True;
if ((SVAL(cli->inbuf,smb_vwv2) & 1) == 0) {
DEBUG(0,("server_validate: password server %s allows users as non-guest \
with a bad password.\n", cli->desthost));
DEBUG(0,("server_validate: This is broken (and insecure) behaviour. Please do not \
use this machine as the password server.\n"));
cli_ulogoff(cli);
/*
* Password server has the bug.
*/
bad_password_server = True;
return NT_STATUS_LOGON_FAILURE;
}
cli_ulogoff(cli);
}
} else {
/*
* We have already tested the password server.
* Fail immediately if it has the bug.
*/
if(bad_password_server) {
DEBUG(0,("server_validate: [1] password server %s allows users as non-guest \
with a bad password.\n", cli->desthost));
DEBUG(0,("server_validate: [1] This is broken (and insecure) behaviour. Please do not \
use this machine as the password server.\n"));
return NT_STATUS_LOGON_FAILURE;
}
}
/*
* Now we know the password server will correctly set the guest bit, or is
* not guest enabled, we can try with the real password.
*/
if (!user_info->encrypted) {
/* Plaintext available */
if (!cli_session_setup(cli, user_info->smb_name.str,
(char *)user_info->plaintext_password.data,
user_info->plaintext_password.length,
NULL, 0,
user_info->domain.str)) {
DEBUG(1,("password server %s rejected the password\n", cli->desthost));
/* Make this cli_nt_error() when the conversion is in */
nt_status = cli_nt_error(cli);
} else {
nt_status = NT_STATUS_OK;
}
} else {
if (!cli_session_setup(cli, user_info->smb_name.str,
(char *)user_info->lm_resp.data,
user_info->lm_resp.length,
(char *)user_info->nt_resp.data,
user_info->nt_resp.length,
user_info->domain.str)) {
DEBUG(1,("password server %s rejected the password\n", cli->desthost));
/* Make this cli_nt_error() when the conversion is in */
nt_status = cli_nt_error(cli);
} else {
nt_status = NT_STATUS_OK;
}
}
/* if logged in as guest then reject */
if ((SVAL(cli->inbuf,smb_vwv2) & 1) != 0) {
DEBUG(1,("password server %s gave us guest only\n", cli->desthost));
nt_status = NT_STATUS_LOGON_FAILURE;
}
cli_ulogoff(cli);
if NT_STATUS_IS_OK(nt_status) {
struct passwd *pass = Get_Pwnam(user_info->internal_username.str);
if (pass) {
nt_status = make_server_info_pw(server_info, pass);
} else {
nt_status = NT_STATUS_NO_SUCH_USER;
}
}
if (locally_made_cli) {
cli_shutdown(cli);
}
return(nt_status);
}
NTSTATUS auth_init_smbserver(struct auth_context *auth_context, const char* param, auth_methods **auth_method)
{
if (!make_auth_methods(auth_context, auth_method)) {
return NT_STATUS_NO_MEMORY;
}
(*auth_method)->name = "smbserver";
(*auth_method)->auth = check_smbserver_security;
(*auth_method)->get_chal = auth_get_challenge_server;
(*auth_method)->send_keepalive = send_server_keepalive;
(*auth_method)->free_private_data = free_server_private_data;
return NT_STATUS_OK;
}

132
source4/auth/auth_unix.c Normal file
View File

@ -0,0 +1,132 @@
/*
Unix SMB/CIFS implementation.
Password and authentication handling
Copyright (C) Andrew Bartlett 2001
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "includes.h"
#undef DBGC_CLASS
#define DBGC_CLASS DBGC_AUTH
/**
* update the encrypted smbpasswd file from the plaintext username and password
*
* this ugly hack needs to die, but not quite yet, I think people still use it...
**/
static BOOL update_smbpassword_file(const char *user, const char *password)
{
SAM_ACCOUNT *sampass = NULL;
BOOL ret;
pdb_init_sam(&sampass);
become_root();
ret = pdb_getsampwnam(sampass, user);
unbecome_root();
if(ret == False) {
DEBUG(0,("pdb_getsampwnam returned NULL\n"));
pdb_free_sam(&sampass);
return False;
}
/*
* Remove the account disabled flag - we are updating the
* users password from a login.
*/
if (!pdb_set_acct_ctrl(sampass, pdb_get_acct_ctrl(sampass) & ~ACB_DISABLED, PDB_CHANGED)) {
pdb_free_sam(&sampass);
return False;
}
if (!pdb_set_plaintext_passwd (sampass, password)) {
pdb_free_sam(&sampass);
return False;
}
/* Now write it into the file. */
become_root();
ret = pdb_update_sam_account (sampass);
unbecome_root();
if (ret) {
DEBUG(3,("pdb_update_sam_account returned %d\n",ret));
}
pdb_free_sam(&sampass);
return ret;
}
/** Check a plaintext username/password
*
* Cannot deal with an encrupted password in any manner whatsoever,
* unless the account has a null password.
**/
static NTSTATUS check_unix_security(const struct auth_context *auth_context,
void *my_private_data,
TALLOC_CTX *mem_ctx,
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
NTSTATUS nt_status;
struct passwd *pass = NULL;
become_root();
pass = Get_Pwnam(user_info->internal_username.str);
/** @todo This call assumes a ASCII password, no charset transformation is
done. We may need to revisit this **/
nt_status = pass_check(pass,
pass ? pass->pw_name : user_info->internal_username.str,
(char *)user_info->plaintext_password.data,
user_info->plaintext_password.length-1,
lp_update_encrypted() ?
update_smbpassword_file : NULL,
True);
unbecome_root();
if (NT_STATUS_IS_OK(nt_status)) {
if (pass) {
make_server_info_pw(server_info, pass);
} else {
/* we need to do somthing more useful here */
nt_status = NT_STATUS_NO_SUCH_USER;
}
}
return nt_status;
}
/* module initialisation */
NTSTATUS auth_init_unix(struct auth_context *auth_context, const char* param, auth_methods **auth_method)
{
if (!make_auth_methods(auth_context, auth_method)) {
return NT_STATUS_NO_MEMORY;
}
(*auth_method)->name = "unix";
(*auth_method)->auth = check_unix_security;
return NT_STATUS_OK;
}

1222
source4/auth/auth_util.c Normal file

File diff suppressed because it is too large Load Diff

136
source4/auth/auth_winbind.c Normal file
View File

@ -0,0 +1,136 @@
/*
Unix SMB/CIFS implementation.
Winbind authentication mechnism
Copyright (C) Tim Potter 2000
Copyright (C) Andrew Bartlett 2001 - 2002
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "includes.h"
#undef DBGC_CLASS
#define DBGC_CLASS DBGC_AUTH
static NTSTATUS get_info3_from_ndr(TALLOC_CTX *mem_ctx, struct winbindd_response *response, NET_USER_INFO_3 *info3)
{
uint8 *info3_ndr;
size_t len = response->length - sizeof(response);
prs_struct ps;
if (len > 0) {
info3_ndr = response->extra_data;
if (!prs_init(&ps, len, mem_ctx, UNMARSHALL)) {
return NT_STATUS_NO_MEMORY;
}
prs_copy_data_in(&ps, info3_ndr, len);
prs_set_offset(&ps,0);
if (!net_io_user_info3("", info3, &ps, 1, 3)) {
DEBUG(2, ("get_info3_from_ndr: could not parse info3 struct!\n"));
return NT_STATUS_UNSUCCESSFUL;
}
prs_mem_free(&ps);
return NT_STATUS_OK;
} else {
DEBUG(2, ("get_info3_from_ndr: No info3 struct found!\n"));
return NT_STATUS_UNSUCCESSFUL;
}
}
/* Authenticate a user with a challenge/response */
static NTSTATUS check_winbind_security(const struct auth_context *auth_context,
void *my_private_data,
TALLOC_CTX *mem_ctx,
const auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info)
{
struct winbindd_request request;
struct winbindd_response response;
NSS_STATUS result;
NTSTATUS nt_status;
NET_USER_INFO_3 info3;
if (!user_info) {
return NT_STATUS_INVALID_PARAMETER;
}
if (!auth_context) {
DEBUG(3,("Password for user %s cannot be checked because we have no auth_info to get the challenge from.\n",
user_info->internal_username.str));
return NT_STATUS_UNSUCCESSFUL;
}
/* Send off request */
ZERO_STRUCT(request);
ZERO_STRUCT(response);
request.data.auth_crap.flags = WINBIND_PAM_INFO3_NDR;
push_utf8_fstring(request.data.auth_crap.user,
user_info->smb_name.str);
push_utf8_fstring(request.data.auth_crap.domain,
user_info->domain.str);
push_utf8_fstring(request.data.auth_crap.workstation,
user_info->wksta_name.str);
memcpy(request.data.auth_crap.chal, auth_context->challenge.data, sizeof(request.data.auth_crap.chal));
request.data.auth_crap.lm_resp_len = MIN(user_info->lm_resp.length,
sizeof(request.data.auth_crap.lm_resp));
request.data.auth_crap.nt_resp_len = MIN(user_info->nt_resp.length,
sizeof(request.data.auth_crap.nt_resp));
memcpy(request.data.auth_crap.lm_resp, user_info->lm_resp.data,
request.data.auth_crap.lm_resp_len);
memcpy(request.data.auth_crap.nt_resp, user_info->nt_resp.data,
request.data.auth_crap.nt_resp_len);
result = winbindd_request(WINBINDD_PAM_AUTH_CRAP, &request, &response);
nt_status = NT_STATUS(response.data.auth.nt_status);
if (result == NSS_STATUS_SUCCESS && response.extra_data) {
if (NT_STATUS_IS_OK(nt_status)) {
if (NT_STATUS_IS_OK(nt_status = get_info3_from_ndr(mem_ctx, &response, &info3))) {
nt_status =
make_server_info_info3(mem_ctx,
user_info->internal_username.str,
user_info->smb_name.str,
user_info->domain.str,
server_info,
&info3);
}
}
} else if (NT_STATUS_IS_OK(nt_status)) {
nt_status = NT_STATUS_UNSUCCESSFUL;
}
return nt_status;
}
/* module initialisation */
NTSTATUS auth_init_winbind(struct auth_context *auth_context, const char *param, auth_methods **auth_method)
{
if (!make_auth_methods(auth_context, auth_method))
return NT_STATUS_NO_MEMORY;
(*auth_method)->name = "winbind";
(*auth_method)->auth = check_winbind_security;
return NT_STATUS_OK;
}

875
source4/auth/pampass.c Normal file
View File

@ -0,0 +1,875 @@
/*
Unix SMB/CIFS implementation.
PAM Password checking
Copyright (C) Andrew Tridgell 1992-2001
Copyright (C) John H Terpsta 1999-2001
Copyright (C) Andrew Bartlett 2001
Copyright (C) Jeremy Allison 2001
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/*
* This module provides PAM based functions for validation of
* username/password pairs, account managment, session and access control.
* Note: SMB password checking is done in smbpass.c
*/
#include "includes.h"
#undef DBGC_CLASS
#define DBGC_CLASS DBGC_AUTH
#ifdef WITH_PAM
/*******************************************************************
* Handle PAM authentication
* - Access, Authentication, Session, Password
* Note: See PAM Documentation and refer to local system PAM implementation
* which determines what actions/limitations/allowances become affected.
*********************************************************************/
#include <security/pam_appl.h>
/*
* Structure used to communicate between the conversation function
* and the server_login/change password functions.
*/
struct smb_pam_userdata {
const char *PAM_username;
const char *PAM_password;
const char *PAM_newpassword;
};
typedef int (*smb_pam_conv_fn)(int, const struct pam_message **, struct pam_response **, void *appdata_ptr);
/*
* Macros to help make life easy
*/
#define COPY_STRING(s) (s) ? strdup(s) : NULL
/*******************************************************************
PAM error handler.
*********************************************************************/
static BOOL smb_pam_error_handler(pam_handle_t *pamh, int pam_error, const char *msg, int dbglvl)
{
if( pam_error != PAM_SUCCESS) {
DEBUG(dbglvl, ("smb_pam_error_handler: PAM: %s : %s\n",
msg, pam_strerror(pamh, pam_error)));
return False;
}
return True;
}
/*******************************************************************
This function is a sanity check, to make sure that we NEVER report
failure as sucess.
*********************************************************************/
static BOOL smb_pam_nt_status_error_handler(pam_handle_t *pamh, int pam_error,
const char *msg, int dbglvl,
NTSTATUS *nt_status)
{
*nt_status = pam_to_nt_status(pam_error);
if (smb_pam_error_handler(pamh, pam_error, msg, dbglvl))
return True;
if (NT_STATUS_IS_OK(*nt_status)) {
/* Complain LOUDLY */
DEBUG(0, ("smb_pam_nt_status_error_handler: PAM: BUG: PAM and NT_STATUS \
error MISMATCH, forcing to NT_STATUS_LOGON_FAILURE"));
*nt_status = NT_STATUS_LOGON_FAILURE;
}
return False;
}
/*
* PAM conversation function
* Here we assume (for now, at least) that echo on means login name, and
* echo off means password.
*/
static int smb_pam_conv(int num_msg,
const struct pam_message **msg,
struct pam_response **resp,
void *appdata_ptr)
{
int replies = 0;
struct pam_response *reply = NULL;
struct smb_pam_userdata *udp = (struct smb_pam_userdata *)appdata_ptr;
*resp = NULL;
if (num_msg <= 0)
return PAM_CONV_ERR;
/*
* Apparantly HPUX has a buggy PAM that doesn't support the
* appdata_ptr. Fail if this is the case. JRA.
*/
if (udp == NULL) {
DEBUG(0,("smb_pam_conv: PAM on this system is broken - appdata_ptr == NULL !\n"));
return PAM_CONV_ERR;
}
reply = malloc(sizeof(struct pam_response) * num_msg);
if (!reply)
return PAM_CONV_ERR;
memset(reply, '\0', sizeof(struct pam_response) * num_msg);
for (replies = 0; replies < num_msg; replies++) {
switch (msg[replies]->msg_style) {
case PAM_PROMPT_ECHO_ON:
reply[replies].resp_retcode = PAM_SUCCESS;
reply[replies].resp = COPY_STRING(udp->PAM_username);
/* PAM frees resp */
break;
case PAM_PROMPT_ECHO_OFF:
reply[replies].resp_retcode = PAM_SUCCESS;
reply[replies].resp = COPY_STRING(udp->PAM_password);
/* PAM frees resp */
break;
case PAM_TEXT_INFO:
/* fall through */
case PAM_ERROR_MSG:
/* ignore it... */
reply[replies].resp_retcode = PAM_SUCCESS;
reply[replies].resp = NULL;
break;
default:
/* Must be an error of some sort... */
SAFE_FREE(reply);
return PAM_CONV_ERR;
}
}
if (reply)
*resp = reply;
return PAM_SUCCESS;
}
/*
* PAM password change conversation function
* Here we assume (for now, at least) that echo on means login name, and
* echo off means password.
*/
static void special_char_sub(char *buf)
{
all_string_sub(buf, "\\n", "", 0);
all_string_sub(buf, "\\r", "", 0);
all_string_sub(buf, "\\s", " ", 0);
all_string_sub(buf, "\\t", "\t", 0);
}
static void pwd_sub(char *buf, const char *username, const char *oldpass, const char *newpass)
{
fstring_sub(buf, "%u", username);
all_string_sub(buf, "%o", oldpass, sizeof(fstring));
all_string_sub(buf, "%n", newpass, sizeof(fstring));
}
struct chat_struct {
struct chat_struct *next, *prev;
fstring prompt;
fstring reply;
};
/**************************************************************
Create a linked list containing chat data.
***************************************************************/
static struct chat_struct *make_pw_chat(char *p)
{
fstring prompt;
fstring reply;
struct chat_struct *list = NULL;
struct chat_struct *t;
struct chat_struct *tmp;
while (1) {
t = (struct chat_struct *)malloc(sizeof(*t));
if (!t) {
DEBUG(0,("make_pw_chat: malloc failed!\n"));
return NULL;
}
ZERO_STRUCTP(t);
DLIST_ADD_END(list, t, tmp);
if (!next_token(&p, prompt, NULL, sizeof(fstring)))
break;
if (strequal(prompt,"."))
fstrcpy(prompt,"*");
special_char_sub(prompt);
fstrcpy(t->prompt, prompt);
strlower(t->prompt);
trim_string(t->prompt, " ", " ");
if (!next_token(&p, reply, NULL, sizeof(fstring)))
break;
if (strequal(reply,"."))
fstrcpy(reply,"");
special_char_sub(reply);
fstrcpy(t->reply, reply);
strlower(t->reply);
trim_string(t->reply, " ", " ");
}
return list;
}
static void free_pw_chat(struct chat_struct *list)
{
while (list) {
struct chat_struct *old_head = list;
DLIST_REMOVE(list, list);
SAFE_FREE(old_head);
}
}
static int smb_pam_passchange_conv(int num_msg,
const struct pam_message **msg,
struct pam_response **resp,
void *appdata_ptr)
{
int replies = 0;
struct pam_response *reply = NULL;
fstring current_prompt;
fstring current_reply;
struct smb_pam_userdata *udp = (struct smb_pam_userdata *)appdata_ptr;
struct chat_struct *pw_chat= make_pw_chat(lp_passwd_chat());
struct chat_struct *t;
BOOL found;
*resp = NULL;
DEBUG(10,("smb_pam_passchange_conv: starting converstation for %d messages\n", num_msg));
if (num_msg <= 0)
return PAM_CONV_ERR;
if (pw_chat == NULL)
return PAM_CONV_ERR;
/*
* Apparantly HPUX has a buggy PAM that doesn't support the
* appdata_ptr. Fail if this is the case. JRA.
*/
if (udp == NULL) {
DEBUG(0,("smb_pam_passchange_conv: PAM on this system is broken - appdata_ptr == NULL !\n"));
free_pw_chat(pw_chat);
return PAM_CONV_ERR;
}
reply = malloc(sizeof(struct pam_response) * num_msg);
if (!reply) {
DEBUG(0,("smb_pam_passchange_conv: malloc for reply failed!\n"));
free_pw_chat(pw_chat);
return PAM_CONV_ERR;
}
for (replies = 0; replies < num_msg; replies++) {
found = False;
DEBUG(10,("smb_pam_passchange_conv: Processing message %d\n", replies));
switch (msg[replies]->msg_style) {
case PAM_PROMPT_ECHO_ON:
DEBUG(10,("smb_pam_passchange_conv: PAM_PROMPT_ECHO_ON: PAM said: %s\n", msg[replies]->msg));
fstrcpy(current_prompt, msg[replies]->msg);
trim_string(current_prompt, " ", " ");
for (t=pw_chat; t; t=t->next) {
DEBUG(10,("smb_pam_passchange_conv: PAM_PROMPT_ECHO_ON: trying to match |%s| to |%s|\n",
t->prompt, current_prompt ));
if (unix_wild_match(t->prompt, current_prompt) == 0) {
fstrcpy(current_reply, t->reply);
DEBUG(10,("smb_pam_passchange_conv: PAM_PROMPT_ECHO_ON: We sent: %s\n", current_reply));
pwd_sub(current_reply, udp->PAM_username, udp->PAM_password, udp->PAM_newpassword);
#ifdef DEBUG_PASSWORD
DEBUG(100,("smb_pam_passchange_conv: PAM_PROMPT_ECHO_ON: We actualy sent: %s\n", current_reply));
#endif
reply[replies].resp_retcode = PAM_SUCCESS;
reply[replies].resp = COPY_STRING(current_reply);
found = True;
break;
}
}
/* PAM frees resp */
if (!found) {
DEBUG(3,("smb_pam_passchange_conv: Could not find reply for PAM prompt: %s\n",msg[replies]->msg));
free_pw_chat(pw_chat);
SAFE_FREE(reply);
return PAM_CONV_ERR;
}
break;
case PAM_PROMPT_ECHO_OFF:
DEBUG(10,("smb_pam_passchange_conv: PAM_PROMPT_ECHO_OFF: PAM said: %s\n", msg[replies]->msg));
fstrcpy(current_prompt, msg[replies]->msg);
trim_string(current_prompt, " ", " ");
for (t=pw_chat; t; t=t->next) {
DEBUG(10,("smb_pam_passchange_conv: PAM_PROMPT_ECHO_OFF: trying to match |%s| to |%s|\n",
t->prompt, current_prompt ));
if (unix_wild_match(t->prompt, current_prompt) == 0) {
fstrcpy(current_reply, t->reply);
DEBUG(10,("smb_pam_passchange_conv: PAM_PROMPT_ECHO_OFF: We sent: %s\n", current_reply));
pwd_sub(current_reply, udp->PAM_username, udp->PAM_password, udp->PAM_newpassword);
reply[replies].resp_retcode = PAM_SUCCESS;
reply[replies].resp = COPY_STRING(current_reply);
#ifdef DEBUG_PASSWORD
DEBUG(100,("smb_pam_passchange_conv: PAM_PROMPT_ECHO_OFF: We actualy sent: %s\n", current_reply));
#endif
found = True;
break;
}
}
/* PAM frees resp */
if (!found) {
DEBUG(3,("smb_pam_passchange_conv: Could not find reply for PAM prompt: %s\n",msg[replies]->msg));
free_pw_chat(pw_chat);
SAFE_FREE(reply);
return PAM_CONV_ERR;
}
break;
case PAM_TEXT_INFO:
/* fall through */
case PAM_ERROR_MSG:
/* ignore it... */
reply[replies].resp_retcode = PAM_SUCCESS;
reply[replies].resp = NULL;
break;
default:
/* Must be an error of some sort... */
free_pw_chat(pw_chat);
SAFE_FREE(reply);
return PAM_CONV_ERR;
}
}
free_pw_chat(pw_chat);
if (reply)
*resp = reply;
return PAM_SUCCESS;
}
/***************************************************************************
Free up a malloced pam_conv struct.
****************************************************************************/
static void smb_free_pam_conv(struct pam_conv *pconv)
{
if (pconv)
SAFE_FREE(pconv->appdata_ptr);
SAFE_FREE(pconv);
}
/***************************************************************************
Allocate a pam_conv struct.
****************************************************************************/
static struct pam_conv *smb_setup_pam_conv(smb_pam_conv_fn smb_pam_conv_fnptr, const char *user,
const char *passwd, const char *newpass)
{
struct pam_conv *pconv = (struct pam_conv *)malloc(sizeof(struct pam_conv));
struct smb_pam_userdata *udp = (struct smb_pam_userdata *)malloc(sizeof(struct smb_pam_userdata));
if (pconv == NULL || udp == NULL) {
SAFE_FREE(pconv);
SAFE_FREE(udp);
return NULL;
}
udp->PAM_username = user;
udp->PAM_password = passwd;
udp->PAM_newpassword = newpass;
pconv->conv = smb_pam_conv_fnptr;
pconv->appdata_ptr = (void *)udp;
return pconv;
}
/*
* PAM Closing out cleanup handler
*/
static BOOL smb_pam_end(pam_handle_t *pamh, struct pam_conv *smb_pam_conv_ptr)
{
int pam_error;
smb_free_pam_conv(smb_pam_conv_ptr);
if( pamh != NULL ) {
pam_error = pam_end(pamh, 0);
if(smb_pam_error_handler(pamh, pam_error, "End Cleanup Failed", 2) == True) {
DEBUG(4, ("smb_pam_end: PAM: PAM_END OK.\n"));
return True;
}
}
DEBUG(2,("smb_pam_end: PAM: not initialised"));
return False;
}
/*
* Start PAM authentication for specified account
*/
static BOOL smb_pam_start(pam_handle_t **pamh, const char *user, const char *rhost, struct pam_conv *pconv)
{
int pam_error;
const char *our_rhost;
*pamh = (pam_handle_t *)NULL;
DEBUG(4,("smb_pam_start: PAM: Init user: %s\n", user));
pam_error = pam_start("samba", user, pconv, pamh);
if( !smb_pam_error_handler(*pamh, pam_error, "Init Failed", 0)) {
*pamh = (pam_handle_t *)NULL;
return False;
}
if (rhost == NULL) {
our_rhost = client_name();
if (strequal(rhost,"UNKNOWN"))
our_rhost = client_addr();
} else {
our_rhost = rhost;
}
#ifdef PAM_RHOST
DEBUG(4,("smb_pam_start: PAM: setting rhost to: %s\n", our_rhost));
pam_error = pam_set_item(*pamh, PAM_RHOST, our_rhost);
if(!smb_pam_error_handler(*pamh, pam_error, "set rhost failed", 0)) {
smb_pam_end(*pamh, pconv);
*pamh = (pam_handle_t *)NULL;
return False;
}
#endif
#ifdef PAM_TTY
DEBUG(4,("smb_pam_start: PAM: setting tty\n"));
pam_error = pam_set_item(*pamh, PAM_TTY, "samba");
if (!smb_pam_error_handler(*pamh, pam_error, "set tty failed", 0)) {
smb_pam_end(*pamh, pconv);
*pamh = (pam_handle_t *)NULL;
return False;
}
#endif
DEBUG(4,("smb_pam_start: PAM: Init passed for user: %s\n", user));
return True;
}
/*
* PAM Authentication Handler
*/
static NTSTATUS smb_pam_auth(pam_handle_t *pamh, const char *user)
{
int pam_error;
NTSTATUS nt_status = NT_STATUS_LOGON_FAILURE;
/*
* To enable debugging set in /etc/pam.d/samba:
* auth required /lib/security/pam_pwdb.so nullok shadow audit
*/
DEBUG(4,("smb_pam_auth: PAM: Authenticate User: %s\n", user));
pam_error = pam_authenticate(pamh, PAM_SILENT | lp_null_passwords() ? 0 : PAM_DISALLOW_NULL_AUTHTOK);
switch( pam_error ){
case PAM_AUTH_ERR:
DEBUG(2, ("smb_pam_auth: PAM: Athentication Error for user %s\n", user));
break;
case PAM_CRED_INSUFFICIENT:
DEBUG(2, ("smb_pam_auth: PAM: Insufficient Credentials for user %s\n", user));
break;
case PAM_AUTHINFO_UNAVAIL:
DEBUG(2, ("smb_pam_auth: PAM: Authentication Information Unavailable for user %s\n", user));
break;
case PAM_USER_UNKNOWN:
DEBUG(2, ("smb_pam_auth: PAM: Username %s NOT known to Authentication system\n", user));
break;
case PAM_MAXTRIES:
DEBUG(2, ("smb_pam_auth: PAM: One or more authentication modules reports user limit for user %s exceeeded\n", user));
break;
case PAM_ABORT:
DEBUG(0, ("smb_pam_auth: PAM: One or more PAM modules failed to load for user %s\n", user));
break;
case PAM_SUCCESS:
DEBUG(4, ("smb_pam_auth: PAM: User %s Authenticated OK\n", user));
break;
default:
DEBUG(0, ("smb_pam_auth: PAM: UNKNOWN ERROR while authenticating user %s\n", user));
break;
}
smb_pam_nt_status_error_handler(pamh, pam_error, "Authentication Failure", 2, &nt_status);
return nt_status;
}
/*
* PAM Account Handler
*/
static NTSTATUS smb_pam_account(pam_handle_t *pamh, const char * user)
{
int pam_error;
NTSTATUS nt_status = NT_STATUS_ACCOUNT_DISABLED;
DEBUG(4,("smb_pam_account: PAM: Account Management for User: %s\n", user));
pam_error = pam_acct_mgmt(pamh, PAM_SILENT); /* Is user account enabled? */
switch( pam_error ) {
case PAM_AUTHTOK_EXPIRED:
DEBUG(2, ("smb_pam_account: PAM: User %s is valid but password is expired\n", user));
break;
case PAM_ACCT_EXPIRED:
DEBUG(2, ("smb_pam_account: PAM: User %s no longer permitted to access system\n", user));
break;
case PAM_AUTH_ERR:
DEBUG(2, ("smb_pam_account: PAM: There was an authentication error for user %s\n", user));
break;
case PAM_PERM_DENIED:
DEBUG(0, ("smb_pam_account: PAM: User %s is NOT permitted to access system at this time\n", user));
break;
case PAM_USER_UNKNOWN:
DEBUG(0, ("smb_pam_account: PAM: User \"%s\" is NOT known to account management\n", user));
break;
case PAM_SUCCESS:
DEBUG(4, ("smb_pam_account: PAM: Account OK for User: %s\n", user));
break;
default:
DEBUG(0, ("smb_pam_account: PAM: UNKNOWN PAM ERROR (%d) during Account Management for User: %s\n", pam_error, user));
break;
}
smb_pam_nt_status_error_handler(pamh, pam_error, "Account Check Failed", 2, &nt_status);
return nt_status;
}
/*
* PAM Credential Setting
*/
static NTSTATUS smb_pam_setcred(pam_handle_t *pamh, const char * user)
{
int pam_error;
NTSTATUS nt_status = NT_STATUS_NO_TOKEN;
/*
* This will allow samba to aquire a kerberos token. And, when
* exporting an AFS cell, be able to /write/ to this cell.
*/
DEBUG(4,("PAM: Account Management SetCredentials for User: %s\n", user));
pam_error = pam_setcred(pamh, (PAM_ESTABLISH_CRED|PAM_SILENT));
switch( pam_error ) {
case PAM_CRED_UNAVAIL:
DEBUG(0, ("smb_pam_setcred: PAM: Credentials not found for user:%s\n", user ));
break;
case PAM_CRED_EXPIRED:
DEBUG(0, ("smb_pam_setcred: PAM: Credentials for user: \"%s\" EXPIRED!\n", user ));
break;
case PAM_USER_UNKNOWN:
DEBUG(0, ("smb_pam_setcred: PAM: User: \"%s\" is NOT known so can not set credentials!\n", user ));
break;
case PAM_CRED_ERR:
DEBUG(0, ("smb_pam_setcred: PAM: Unknown setcredentials error - unable to set credentials for %s\n", user ));
break;
case PAM_SUCCESS:
DEBUG(4, ("smb_pam_setcred: PAM: SetCredentials OK for User: %s\n", user));
break;
default:
DEBUG(0, ("smb_pam_setcred: PAM: UNKNOWN PAM ERROR (%d) during SetCredentials for User: %s\n", pam_error, user));
break;
}
smb_pam_nt_status_error_handler(pamh, pam_error, "Set Credential Failure", 2, &nt_status);
return nt_status;
}
/*
* PAM Internal Session Handler
*/
static BOOL smb_internal_pam_session(pam_handle_t *pamh, const char *user, const char *tty, BOOL flag)
{
int pam_error;
#ifdef PAM_TTY
DEBUG(4,("smb_internal_pam_session: PAM: tty set to: %s\n", tty));
pam_error = pam_set_item(pamh, PAM_TTY, tty);
if (!smb_pam_error_handler(pamh, pam_error, "set tty failed", 0))
return False;
#endif
if (flag) {
pam_error = pam_open_session(pamh, PAM_SILENT);
if (!smb_pam_error_handler(pamh, pam_error, "session setup failed", 0))
return False;
} else {
pam_setcred(pamh, (PAM_DELETE_CRED|PAM_SILENT)); /* We don't care if this fails */
pam_error = pam_close_session(pamh, PAM_SILENT); /* This will probably pick up the error anyway */
if (!smb_pam_error_handler(pamh, pam_error, "session close failed", 0))
return False;
}
return (True);
}
/*
* Internal PAM Password Changer.
*/
static BOOL smb_pam_chauthtok(pam_handle_t *pamh, const char * user)
{
int pam_error;
DEBUG(4,("smb_pam_chauthtok: PAM: Password Change for User: %s\n", user));
pam_error = pam_chauthtok(pamh, PAM_SILENT); /* Change Password */
switch( pam_error ) {
case PAM_AUTHTOK_ERR:
DEBUG(2, ("PAM: unable to obtain the new authentication token - is password to weak?\n"));
break;
/* This doesn't seem to be defined on Solaris. JRA */
#ifdef PAM_AUTHTOK_RECOVER_ERR
case PAM_AUTHTOK_RECOVER_ERR:
DEBUG(2, ("PAM: unable to obtain the old authentication token - was the old password wrong?.\n"));
break;
#endif
case PAM_AUTHTOK_LOCK_BUSY:
DEBUG(2, ("PAM: unable to change the authentication token since it is currently locked.\n"));
break;
case PAM_AUTHTOK_DISABLE_AGING:
DEBUG(2, ("PAM: Authentication token aging has been disabled.\n"));
break;
case PAM_PERM_DENIED:
DEBUG(0, ("PAM: Permission denied.\n"));
break;
case PAM_TRY_AGAIN:
DEBUG(0, ("PAM: Could not update all authentication token(s). No authentication tokens were updated.\n"));
break;
case PAM_USER_UNKNOWN:
DEBUG(0, ("PAM: User not known to PAM\n"));
break;
case PAM_SUCCESS:
DEBUG(4, ("PAM: Account OK for User: %s\n", user));
break;
default:
DEBUG(0, ("PAM: UNKNOWN PAM ERROR (%d) for User: %s\n", pam_error, user));
}
if(!smb_pam_error_handler(pamh, pam_error, "Password Change Failed", 2)) {
return False;
}
/* If this point is reached, the password has changed. */
return True;
}
/*
* PAM Externally accessible Session handler
*/
BOOL smb_pam_claim_session(char *user, char *tty, char *rhost)
{
pam_handle_t *pamh = NULL;
struct pam_conv *pconv = NULL;
/* Ignore PAM if told to. */
if (!lp_obey_pam_restrictions())
return True;
if ((pconv = smb_setup_pam_conv(smb_pam_conv, user, NULL, NULL)) == NULL)
return False;
if (!smb_pam_start(&pamh, user, rhost, pconv))
return False;
if (!smb_internal_pam_session(pamh, user, tty, True)) {
smb_pam_end(pamh, pconv);
return False;
}
return smb_pam_end(pamh, pconv);
}
/*
* PAM Externally accessible Session handler
*/
BOOL smb_pam_close_session(char *user, char *tty, char *rhost)
{
pam_handle_t *pamh = NULL;
struct pam_conv *pconv = NULL;
/* Ignore PAM if told to. */
if (!lp_obey_pam_restrictions())
return True;
if ((pconv = smb_setup_pam_conv(smb_pam_conv, user, NULL, NULL)) == NULL)
return False;
if (!smb_pam_start(&pamh, user, rhost, pconv))
return False;
if (!smb_internal_pam_session(pamh, user, tty, False)) {
smb_pam_end(pamh, pconv);
return False;
}
return smb_pam_end(pamh, pconv);
}
/*
* PAM Externally accessible Account handler
*/
NTSTATUS smb_pam_accountcheck(const char * user)
{
NTSTATUS nt_status = NT_STATUS_ACCOUNT_DISABLED;
pam_handle_t *pamh = NULL;
struct pam_conv *pconv = NULL;
/* Ignore PAM if told to. */
if (!lp_obey_pam_restrictions())
return NT_STATUS_OK;
if ((pconv = smb_setup_pam_conv(smb_pam_conv, user, NULL, NULL)) == NULL)
return NT_STATUS_NO_MEMORY;
if (!smb_pam_start(&pamh, user, NULL, pconv))
return NT_STATUS_ACCOUNT_DISABLED;
if (!NT_STATUS_IS_OK(nt_status = smb_pam_account(pamh, user)))
DEBUG(0, ("smb_pam_accountcheck: PAM: Account Validation Failed - Rejecting User %s!\n", user));
smb_pam_end(pamh, pconv);
return nt_status;
}
/*
* PAM Password Validation Suite
*/
NTSTATUS smb_pam_passcheck(const char * user, const char * password)
{
pam_handle_t *pamh = NULL;
NTSTATUS nt_status = NT_STATUS_LOGON_FAILURE;
struct pam_conv *pconv = NULL;
/*
* Note we can't ignore PAM here as this is the only
* way of doing auths on plaintext passwords when
* compiled --with-pam.
*/
if ((pconv = smb_setup_pam_conv(smb_pam_conv, user, password, NULL)) == NULL)
return NT_STATUS_LOGON_FAILURE;
if (!smb_pam_start(&pamh, user, NULL, pconv))
return NT_STATUS_LOGON_FAILURE;
if (!NT_STATUS_IS_OK(nt_status = smb_pam_auth(pamh, user))) {
DEBUG(0, ("smb_pam_passcheck: PAM: smb_pam_auth failed - Rejecting User %s !\n", user));
smb_pam_end(pamh, pconv);
return nt_status;
}
if (!NT_STATUS_IS_OK(nt_status = smb_pam_account(pamh, user))) {
DEBUG(0, ("smb_pam_passcheck: PAM: smb_pam_account failed - Rejecting User %s !\n", user));
smb_pam_end(pamh, pconv);
return nt_status;
}
if (!NT_STATUS_IS_OK(nt_status = smb_pam_setcred(pamh, user))) {
DEBUG(0, ("smb_pam_passcheck: PAM: smb_pam_setcred failed - Rejecting User %s !\n", user));
smb_pam_end(pamh, pconv);
return nt_status;
}
smb_pam_end(pamh, pconv);
return nt_status;
}
/*
* PAM Password Change Suite
*/
BOOL smb_pam_passchange(const char * user, const char * oldpassword, const char * newpassword)
{
/* Appropriate quantities of root should be obtained BEFORE calling this function */
struct pam_conv *pconv = NULL;
pam_handle_t *pamh = NULL;
if ((pconv = smb_setup_pam_conv(smb_pam_passchange_conv, user, oldpassword, newpassword)) == NULL)
return False;
if(!smb_pam_start(&pamh, user, NULL, pconv))
return False;
if (!smb_pam_chauthtok(pamh, user)) {
DEBUG(0, ("smb_pam_passchange: PAM: Password Change Failed for user %s!\n", user));
smb_pam_end(pamh, pconv);
return False;
}
return smb_pam_end(pamh, pconv);
}
#else
/* If PAM not used, no PAM restrictions on accounts. */
NTSTATUS smb_pam_accountcheck(const char * user)
{
return NT_STATUS_OK;
}
/* If PAM not used, also no PAM restrictions on sessions. */
BOOL smb_pam_claim_session(char *user, char *tty, char *rhost)
{
return True;
}
/* If PAM not used, also no PAM restrictions on sessions. */
BOOL smb_pam_close_session(char *in_user, char *tty, char *rhost)
{
return True;
}
#endif /* WITH_PAM */

784
source4/auth/pass_check.c Normal file
View File

@ -0,0 +1,784 @@
/*
Unix SMB/CIFS implementation.
Password checking
Copyright (C) Andrew Tridgell 1992-1998
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* this module is for checking a username/password against a system
password database. The SMB encrypted password support is elsewhere */
#include "includes.h"
#undef DBGC_CLASS
#define DBGC_CLASS DBGC_AUTH
/* these are kept here to keep the string_combinations function simple */
static fstring this_user;
#if !defined(WITH_PAM)
static fstring this_salt;
static fstring this_crypted;
#endif
#ifdef WITH_AFS
#include <afs/stds.h>
#include <afs/kautils.h>
/*******************************************************************
check on AFS authentication
********************************************************************/
static BOOL afs_auth(char *user, char *password)
{
long password_expires = 0;
char *reason;
/* For versions of AFS prior to 3.3, this routine has few arguments, */
/* but since I can't find the old documentation... :-) */
setpag();
if (ka_UserAuthenticateGeneral
(KA_USERAUTH_VERSION + KA_USERAUTH_DOSETPAG, user, (char *)0, /* instance */
(char *)0, /* cell */
password, 0, /* lifetime, default */
&password_expires, /*days 'til it expires */
0, /* spare 2 */
&reason) == 0)
{
return (True);
}
DEBUG(1,
("AFS authentication for \"%s\" failed (%s)\n", user, reason));
return (False);
}
#endif
#ifdef WITH_DFS
#include <dce/dce_error.h>
#include <dce/sec_login.h>
/*****************************************************************
This new version of the DFS_AUTH code was donated by Karsten Muuss
<muuss@or.uni-bonn.de>. It fixes the following problems with the
old code :
- Server credentials may expire
- Client credential cache files have wrong owner
- purge_context() function is called with invalid argument
This new code was modified to ensure that on exit the uid/gid is
still root, and the original directory is restored. JRA.
******************************************************************/
sec_login_handle_t my_dce_sec_context;
int dcelogin_atmost_once = 0;
/*******************************************************************
check on a DCE/DFS authentication
********************************************************************/
static BOOL dfs_auth(char *user, char *password)
{
error_status_t err;
int err2;
int prterr;
signed32 expire_time, current_time;
boolean32 password_reset;
struct passwd *pw;
sec_passwd_rec_t passwd_rec;
sec_login_auth_src_t auth_src = sec_login_auth_src_network;
unsigned char dce_errstr[dce_c_error_string_len];
gid_t egid;
if (dcelogin_atmost_once)
return (False);
#ifdef HAVE_CRYPT
/*
* We only go for a DCE login context if the given password
* matches that stored in the local password file..
* Assumes local passwd file is kept in sync w/ DCE RGY!
*/
if (strcmp((char *)crypt(password, this_salt), this_crypted))
{
return (False);
}
#endif
sec_login_get_current_context(&my_dce_sec_context, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE can't get current context. %s\n", dce_errstr));
return (False);
}
sec_login_certify_identity(my_dce_sec_context, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE can't get current context. %s\n", dce_errstr));
return (False);
}
sec_login_get_expiration(my_dce_sec_context, &expire_time, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE can't get expiration. %s\n", dce_errstr));
return (False);
}
time(&current_time);
if (expire_time < (current_time + 60))
{
struct passwd *pw;
sec_passwd_rec_t *key;
sec_login_get_pwent(my_dce_sec_context,
(sec_login_passwd_t *) & pw, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE can't get pwent. %s\n", dce_errstr));
return (False);
}
sec_login_refresh_identity(my_dce_sec_context, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE can't refresh identity. %s\n",
dce_errstr));
return (False);
}
sec_key_mgmt_get_key(rpc_c_authn_dce_secret, NULL,
(unsigned char *)pw->pw_name,
sec_c_key_version_none,
(void **)&key, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE can't get key for %s. %s\n",
pw->pw_name, dce_errstr));
return (False);
}
sec_login_valid_and_cert_ident(my_dce_sec_context, key,
&password_reset, &auth_src,
&err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0,
("DCE can't validate and certify identity for %s. %s\n",
pw->pw_name, dce_errstr));
}
sec_key_mgmt_free_key(key, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE can't free key.\n", dce_errstr));
}
}
if (sec_login_setup_identity((unsigned char *)user,
sec_login_no_flags,
&my_dce_sec_context, &err) == 0)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE Setup Identity for %s failed: %s\n",
user, dce_errstr));
return (False);
}
sec_login_get_pwent(my_dce_sec_context,
(sec_login_passwd_t *) & pw, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE can't get pwent. %s\n", dce_errstr));
return (False);
}
sec_login_purge_context(&my_dce_sec_context, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE can't purge context. %s\n", dce_errstr));
return (False);
}
/*
* NB. I'd like to change these to call something like change_to_user()
* instead but currently we don't have a connection
* context to become the correct user. This is already
* fairly platform specific code however, so I think
* this should be ok. I have added code to go
* back to being root on error though. JRA.
*/
egid = getegid();
set_effective_gid(pw->pw_gid);
set_effective_uid(pw->pw_uid);
if (sec_login_setup_identity((unsigned char *)user,
sec_login_no_flags,
&my_dce_sec_context, &err) == 0)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE Setup Identity for %s failed: %s\n",
user, dce_errstr));
goto err;
}
sec_login_get_pwent(my_dce_sec_context,
(sec_login_passwd_t *) & pw, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE can't get pwent. %s\n", dce_errstr));
goto err;
}
passwd_rec.version_number = sec_passwd_c_version_none;
passwd_rec.pepper = NULL;
passwd_rec.key.key_type = sec_passwd_plain;
passwd_rec.key.tagged_union.plain = (idl_char *) password;
sec_login_validate_identity(my_dce_sec_context,
&passwd_rec, &password_reset,
&auth_src, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0,
("DCE Identity Validation failed for principal %s: %s\n",
user, dce_errstr));
goto err;
}
sec_login_certify_identity(my_dce_sec_context, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE certify identity failed: %s\n", dce_errstr));
goto err;
}
if (auth_src != sec_login_auth_src_network)
{
DEBUG(0, ("DCE context has no network credentials.\n"));
}
sec_login_set_context(my_dce_sec_context, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0,
("DCE login failed for principal %s, cant set context: %s\n",
user, dce_errstr));
sec_login_purge_context(&my_dce_sec_context, &err);
goto err;
}
sec_login_get_pwent(my_dce_sec_context,
(sec_login_passwd_t *) & pw, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE can't get pwent. %s\n", dce_errstr));
goto err;
}
DEBUG(0, ("DCE login succeeded for principal %s on pid %d\n",
user, sys_getpid()));
DEBUG(3, ("DCE principal: %s\n"
" uid: %d\n"
" gid: %d\n",
pw->pw_name, pw->pw_uid, pw->pw_gid));
DEBUG(3, (" info: %s\n"
" dir: %s\n"
" shell: %s\n",
pw->pw_gecos, pw->pw_dir, pw->pw_shell));
sec_login_get_expiration(my_dce_sec_context, &expire_time, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0, ("DCE can't get expiration. %s\n", dce_errstr));
goto err;
}
set_effective_uid(0);
set_effective_gid(0);
DEBUG(0,
("DCE context expires: %s", asctime(localtime(&expire_time))));
dcelogin_atmost_once = 1;
return (True);
err:
/* Go back to root, JRA. */
set_effective_uid(0);
set_effective_gid(egid);
return (False);
}
void dfs_unlogin(void)
{
error_status_t err;
int err2;
unsigned char dce_errstr[dce_c_error_string_len];
sec_login_purge_context(&my_dce_sec_context, &err);
if (err != error_status_ok)
{
dce_error_inq_text(err, dce_errstr, &err2);
DEBUG(0,
("DCE purge login context failed for server instance %d: %s\n",
sys_getpid(), dce_errstr));
}
}
#endif
#ifdef LINUX_BIGCRYPT
/****************************************************************************
an enhanced crypt for Linux to handle password longer than 8 characters
****************************************************************************/
static int linux_bigcrypt(char *password, char *salt1, char *crypted)
{
#define LINUX_PASSWORD_SEG_CHARS 8
char salt[3];
int i;
StrnCpy(salt, salt1, 2);
crypted += 2;
for (i = strlen(password); i > 0; i -= LINUX_PASSWORD_SEG_CHARS) {
char *p = crypt(password, salt) + 2;
if (strncmp(p, crypted, LINUX_PASSWORD_SEG_CHARS) != 0)
return (0);
password += LINUX_PASSWORD_SEG_CHARS;
crypted += strlen(p);
}
return (1);
}
#endif
#ifdef OSF1_ENH_SEC
/****************************************************************************
an enhanced crypt for OSF1
****************************************************************************/
static char *osf1_bigcrypt(char *password, char *salt1)
{
static char result[AUTH_MAX_PASSWD_LENGTH] = "";
char *p1;
char *p2 = password;
char salt[3];
int i;
int parts = strlen(password) / AUTH_CLEARTEXT_SEG_CHARS;
if (strlen(password) % AUTH_CLEARTEXT_SEG_CHARS)
parts++;
StrnCpy(salt, salt1, 2);
StrnCpy(result, salt1, 2);
result[2] = '\0';
for (i = 0; i < parts; i++) {
p1 = crypt(p2, salt);
strncat(result, p1 + 2,
AUTH_MAX_PASSWD_LENGTH - strlen(p1 + 2) - 1);
StrnCpy(salt, &result[2 + i * AUTH_CIPHERTEXT_SEG_CHARS], 2);
p2 += AUTH_CLEARTEXT_SEG_CHARS;
}
return (result);
}
#endif
/****************************************************************************
apply a function to upper/lower case combinations
of a string and return true if one of them returns true.
try all combinations with N uppercase letters.
offset is the first char to try and change (start with 0)
it assumes the string starts lowercased
****************************************************************************/
static NTSTATUS string_combinations2(char *s, int offset, NTSTATUS (*fn) (const char *),
int N)
{
int len = strlen(s);
int i;
NTSTATUS nt_status;
#ifdef PASSWORD_LENGTH
len = MIN(len, PASSWORD_LENGTH);
#endif
if (N <= 0 || offset >= len)
return (fn(s));
for (i = offset; i < (len - (N - 1)); i++) {
char c = s[i];
if (!islower(c))
continue;
s[i] = toupper(c);
if (!NT_STATUS_EQUAL(nt_status = string_combinations2(s, i + 1, fn, N - 1),NT_STATUS_WRONG_PASSWORD)) {
return (nt_status);
}
s[i] = c;
}
return (NT_STATUS_WRONG_PASSWORD);
}
/****************************************************************************
apply a function to upper/lower case combinations
of a string and return true if one of them returns true.
try all combinations with up to N uppercase letters.
offset is the first char to try and change (start with 0)
it assumes the string starts lowercased
****************************************************************************/
static NTSTATUS string_combinations(char *s, NTSTATUS (*fn) (const char *), int N)
{
int n;
NTSTATUS nt_status;
for (n = 1; n <= N; n++)
if (!NT_STATUS_EQUAL(nt_status = string_combinations2(s, 0, fn, n), NT_STATUS_WRONG_PASSWORD))
return nt_status;
return NT_STATUS_WRONG_PASSWORD;
}
/****************************************************************************
core of password checking routine
****************************************************************************/
static NTSTATUS password_check(const char *password)
{
#ifdef WITH_PAM
return smb_pam_passcheck(this_user, password);
#else
BOOL ret;
#ifdef WITH_AFS
if (afs_auth(this_user, password))
return NT_STATUS_OK;
#endif /* WITH_AFS */
#ifdef WITH_DFS
if (dfs_auth(this_user, password))
return NT_STATUS_OK;
#endif /* WITH_DFS */
#ifdef OSF1_ENH_SEC
ret = (strcmp(osf1_bigcrypt(password, this_salt),
this_crypted) == 0);
if (!ret) {
DEBUG(2,
("OSF1_ENH_SEC failed. Trying normal crypt.\n"));
ret = (strcmp((char *)crypt(password, this_salt), this_crypted) == 0);
}
if (ret) {
return NT_STATUS_OK;
} else {
return NT_STATUS_WRONG_PASSWORD;
}
#endif /* OSF1_ENH_SEC */
#ifdef ULTRIX_AUTH
ret = (strcmp((char *)crypt16(password, this_salt), this_crypted) == 0);
if (ret) {
return NT_STATUS_OK;
} else {
return NT_STATUS_WRONG_PASSWORD;
}
#endif /* ULTRIX_AUTH */
#ifdef LINUX_BIGCRYPT
ret = (linux_bigcrypt(password, this_salt, this_crypted));
if (ret) {
return NT_STATUS_OK;
} else {
return NT_STATUS_WRONG_PASSWORD;
}
#endif /* LINUX_BIGCRYPT */
#if defined(HAVE_BIGCRYPT) && defined(HAVE_CRYPT) && defined(USE_BOTH_CRYPT_CALLS)
/*
* Some systems have bigcrypt in the C library but might not
* actually use it for the password hashes (HPUX 10.20) is
* a noteable example. So we try bigcrypt first, followed
* by crypt.
*/
if (strcmp(bigcrypt(password, this_salt), this_crypted) == 0)
return NT_STATUS_OK;
else
ret = (strcmp((char *)crypt(password, this_salt), this_crypted) == 0);
if (ret) {
return NT_STATUS_OK;
} else {
return NT_STATUS_WRONG_PASSWORD;
}
#else /* HAVE_BIGCRYPT && HAVE_CRYPT && USE_BOTH_CRYPT_CALLS */
#ifdef HAVE_BIGCRYPT
ret = (strcmp(bigcrypt(password, this_salt), this_crypted) == 0);
if (ret) {
return NT_STATUS_OK;
} else {
return NT_STATUS_WRONG_PASSWORD;
}
#endif /* HAVE_BIGCRYPT */
#ifndef HAVE_CRYPT
DEBUG(1, ("Warning - no crypt available\n"));
return NT_STATUS_LOGON_FAILURE;
#else /* HAVE_CRYPT */
ret = (strcmp((char *)crypt(password, this_salt), this_crypted) == 0);
if (ret) {
return NT_STATUS_OK;
} else {
return NT_STATUS_WRONG_PASSWORD;
}
#endif /* HAVE_CRYPT */
#endif /* HAVE_BIGCRYPT && HAVE_CRYPT && USE_BOTH_CRYPT_CALLS */
#endif /* WITH_PAM */
}
/****************************************************************************
CHECK if a username/password is OK
the function pointer fn() points to a function to call when a successful
match is found and is used to update the encrypted password file
return NT_STATUS_OK on correct match, appropriate error otherwise
****************************************************************************/
NTSTATUS pass_check(const struct passwd *pass, const char *user, const char *password,
int pwlen, BOOL (*fn) (const char *, const char *), BOOL run_cracker)
{
pstring pass2;
int level = lp_passwordlevel();
NTSTATUS nt_status;
#if DEBUG_PASSWORD
DEBUG(100, ("checking user=[%s] pass=[%s]\n", user, password));
#endif
if (!password)
return NT_STATUS_LOGON_FAILURE;
if (((!*password) || (!pwlen)) && !lp_null_passwords())
return NT_STATUS_LOGON_FAILURE;
#if defined(WITH_PAM)
/*
* If we're using PAM we want to short-circuit all the
* checks below and dive straight into the PAM code.
*/
fstrcpy(this_user, user);
DEBUG(4, ("pass_check: Checking (PAM) password for user %s (l=%d)\n", user, pwlen));
#else /* Not using PAM */
DEBUG(4, ("pass_check: Checking password for user %s (l=%d)\n", user, pwlen));
if (!pass) {
DEBUG(3, ("Couldn't find user %s\n", user));
return NT_STATUS_NO_SUCH_USER;
}
/* Copy into global for the convenience of looping code */
/* Also the place to keep the 'password' no matter what
crazy struct it started in... */
fstrcpy(this_crypted, pass->pw_passwd);
fstrcpy(this_salt, pass->pw_passwd);
#ifdef HAVE_GETSPNAM
{
struct spwd *spass;
/* many shadow systems require you to be root to get
the password, in most cases this should already be
the case when this function is called, except
perhaps for IPC password changing requests */
spass = getspnam(pass->pw_name);
if (spass && spass->sp_pwdp) {
fstrcpy(this_crypted, spass->sp_pwdp);
fstrcpy(this_salt, spass->sp_pwdp);
}
}
#elif defined(IA_UINFO)
{
/* Need to get password with SVR4.2's ia_ functions
instead of get{sp,pw}ent functions. Required by
UnixWare 2.x, tested on version
2.1. (tangent@cyberport.com) */
uinfo_t uinfo;
if (ia_openinfo(pass->pw_name, &uinfo) != -1)
ia_get_logpwd(uinfo, &(pass->pw_passwd));
}
#endif
#ifdef HAVE_GETPRPWNAM
{
struct pr_passwd *pr_pw = getprpwnam(pass->pw_name);
if (pr_pw && pr_pw->ufld.fd_encrypt)
fstrcpy(this_crypted, pr_pw->ufld.fd_encrypt);
}
#endif
#ifdef HAVE_GETPWANAM
{
struct passwd_adjunct *pwret;
pwret = getpwanam(s);
if (pwret && pwret->pwa_passwd)
fstrcpy(this_crypted, pwret->pwa_passwd);
}
#endif
#ifdef OSF1_ENH_SEC
{
struct pr_passwd *mypasswd;
DEBUG(5, ("Checking password for user %s in OSF1_ENH_SEC\n",
user));
mypasswd = getprpwnam(user);
if (mypasswd) {
fstrcpy(this_user, mypasswd->ufld.fd_name);
fstrcpy(this_crypted, mypasswd->ufld.fd_encrypt);
} else {
DEBUG(5,
("OSF1_ENH_SEC: No entry for user %s in protected database !\n",
user));
}
}
#endif
#ifdef ULTRIX_AUTH
{
AUTHORIZATION *ap = getauthuid(pass->pw_uid);
if (ap) {
fstrcpy(this_crypted, ap->a_password);
endauthent();
}
}
#endif
#if defined(HAVE_TRUNCATED_SALT)
/* crypt on some platforms (HPUX in particular)
won't work with more than 2 salt characters. */
this_salt[2] = 0;
#endif
if (!*this_crypted) {
if (!lp_null_passwords()) {
DEBUG(2, ("Disallowing %s with null password\n",
this_user));
return NT_STATUS_LOGON_FAILURE;
}
if (!*password) {
DEBUG(3,
("Allowing access to %s with null password\n",
this_user));
return NT_STATUS_OK;
}
}
#endif /* defined(WITH_PAM) */
/* try it as it came to us */
nt_status = password_check(password);
if NT_STATUS_IS_OK(nt_status) {
if (fn) {
fn(user, password);
}
return (nt_status);
} else if (!NT_STATUS_EQUAL(nt_status, NT_STATUS_WRONG_PASSWORD)) {
/* No point continuing if its not the password thats to blame (ie PAM disabled). */
return (nt_status);
}
if (!run_cracker) {
return (nt_status);
}
/* if the password was given to us with mixed case then we don't
* need to proceed as we know it hasn't been case modified by the
* client */
if (strhasupper(password) && strhaslower(password)) {
return nt_status;
}
/* make a copy of it */
pstrcpy(pass2, password);
/* try all lowercase if it's currently all uppercase */
if (strhasupper(pass2)) {
strlower(pass2);
if NT_STATUS_IS_OK(nt_status = password_check(pass2)) {
if (fn)
fn(user, pass2);
return (nt_status);
}
}
/* give up? */
if (level < 1) {
return NT_STATUS_WRONG_PASSWORD;
}
/* last chance - all combinations of up to level chars upper! */
strlower(pass2);
if (NT_STATUS_IS_OK(nt_status = string_combinations(pass2, password_check, level))) {
if (fn)
fn(user, pass2);
return nt_status;
}
return NT_STATUS_WRONG_PASSWORD;
}

36
source4/autogen.sh Executable file
View File

@ -0,0 +1,36 @@
#! /bin/sh
# Run this script to build samba from CVS.
## first try the default names
AUTOHEADER="autoheader"
AUTOCONF="autoconf"
if which $AUTOCONF > /dev/null
then
:
else
echo "$0: need autoconf 2.53 or later to build samba from CVS" >&2
exit 1
fi
##
## what version do we need?
##
if [ `$AUTOCONF --version | head -1 | cut -d. -f 2` -lt 53 ]; then
## maybe it's installed under a different name (e.g. RedHat 7.3)
AUTOCONF="autoconf-2.53"
AUTOHEADER="autoheader-2.53"
fi
echo "$0: running $AUTOHEADER"
$AUTOHEADER || exit 1
echo "$0: running $AUTOCONF"
$AUTOCONF || exit 1
echo "Now run ./configure and then make."
exit 0

View File

@ -0,0 +1,10 @@
This directory contains autoconf test programs that are too large to
comfortably fit in configure.in.
These programs should test one feature of the OS and exit(0) if it
works or exit(1) if it doesn't work (do _not_ use return)
The programs should be kept simple and to the point. Beautiful/fast
code is not necessary

View File

@ -0,0 +1,852 @@
#if defined(HAVE_UNISTD_H)
#include <unistd.h>
#endif
#include <sys/types.h>
#ifdef HAVE_STRING_H
#include <string.h>
#endif
#ifdef HAVE_STRINGS_H
#include <strings.h>
#endif
#if !defined(HAVE_CRYPT)
/*
This bit of code was derived from the UFC-crypt package which
carries the following copyright
Modified for use by Samba by Andrew Tridgell, October 1994
Note that this routine is only faster on some machines. Under Linux 1.1.51
libc 4.5.26 I actually found this routine to be slightly slower.
Under SunOS I found a huge speedup by using these routines
(a factor of 20 or so)
Warning: I've had a report from Steve Kennedy <steve@gbnet.org>
that this crypt routine may sometimes get the wrong answer. Only
use UFC_CRYT if you really need it.
*/
/*
* UFC-crypt: ultra fast crypt(3) implementation
*
* Copyright (C) 1991-1998, Free Software Foundation, Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public
* License as published by the Free Software Foundation; either
* version 2 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; if not, write to the Free
* Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*
* @(#)crypt_util.c 2.31 02/08/92
*
* Support routines
*
*/
#ifndef long32
#if (SIZEOF_INT == 4)
#define long32 int
#elif (SIZEOF_LONG == 4)
#define long32 long
#elif (SIZEOF_SHORT == 4)
#define long32 short
#else
/* uggh - no 32 bit type?? probably a CRAY. just hope this works ... */
#define long32 int
#endif
#endif
#ifndef long64
#ifdef HAVE_LONGLONG
#define long64 long long long
#endif
#endif
#ifndef ufc_long
#define ufc_long unsigned
#endif
#ifndef _UFC_64_
#define _UFC_32_
#endif
/*
* Permutation done once on the 56 bit
* key derived from the original 8 byte ASCII key.
*/
static int pc1[56] = {
57, 49, 41, 33, 25, 17, 9, 1, 58, 50, 42, 34, 26, 18,
10, 2, 59, 51, 43, 35, 27, 19, 11, 3, 60, 52, 44, 36,
63, 55, 47, 39, 31, 23, 15, 7, 62, 54, 46, 38, 30, 22,
14, 6, 61, 53, 45, 37, 29, 21, 13, 5, 28, 20, 12, 4
};
/*
* How much to rotate each 28 bit half of the pc1 permutated
* 56 bit key before using pc2 to give the i' key
*/
static int rots[16] = {
1, 1, 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 1
};
/*
* Permutation giving the key
* of the i' DES round
*/
static int pc2[48] = {
14, 17, 11, 24, 1, 5, 3, 28, 15, 6, 21, 10,
23, 19, 12, 4, 26, 8, 16, 7, 27, 20, 13, 2,
41, 52, 31, 37, 47, 55, 30, 40, 51, 45, 33, 48,
44, 49, 39, 56, 34, 53, 46, 42, 50, 36, 29, 32
};
/*
* The E expansion table which selects
* bits from the 32 bit intermediate result.
*/
static int esel[48] = {
32, 1, 2, 3, 4, 5, 4, 5, 6, 7, 8, 9,
8, 9, 10, 11, 12, 13, 12, 13, 14, 15, 16, 17,
16, 17, 18, 19, 20, 21, 20, 21, 22, 23, 24, 25,
24, 25, 26, 27, 28, 29, 28, 29, 30, 31, 32, 1
};
static int e_inverse[64];
/*
* Permutation done on the
* result of sbox lookups
*/
static int perm32[32] = {
16, 7, 20, 21, 29, 12, 28, 17, 1, 15, 23, 26, 5, 18, 31, 10,
2, 8, 24, 14, 32, 27, 3, 9, 19, 13, 30, 6, 22, 11, 4, 25
};
/*
* The sboxes
*/
static int sbox[8][4][16]= {
{ { 14, 4, 13, 1, 2, 15, 11, 8, 3, 10, 6, 12, 5, 9, 0, 7 },
{ 0, 15, 7, 4, 14, 2, 13, 1, 10, 6, 12, 11, 9, 5, 3, 8 },
{ 4, 1, 14, 8, 13, 6, 2, 11, 15, 12, 9, 7, 3, 10, 5, 0 },
{ 15, 12, 8, 2, 4, 9, 1, 7, 5, 11, 3, 14, 10, 0, 6, 13 }
},
{ { 15, 1, 8, 14, 6, 11, 3, 4, 9, 7, 2, 13, 12, 0, 5, 10 },
{ 3, 13, 4, 7, 15, 2, 8, 14, 12, 0, 1, 10, 6, 9, 11, 5 },
{ 0, 14, 7, 11, 10, 4, 13, 1, 5, 8, 12, 6, 9, 3, 2, 15 },
{ 13, 8, 10, 1, 3, 15, 4, 2, 11, 6, 7, 12, 0, 5, 14, 9 }
},
{ { 10, 0, 9, 14, 6, 3, 15, 5, 1, 13, 12, 7, 11, 4, 2, 8 },
{ 13, 7, 0, 9, 3, 4, 6, 10, 2, 8, 5, 14, 12, 11, 15, 1 },
{ 13, 6, 4, 9, 8, 15, 3, 0, 11, 1, 2, 12, 5, 10, 14, 7 },
{ 1, 10, 13, 0, 6, 9, 8, 7, 4, 15, 14, 3, 11, 5, 2, 12 }
},
{ { 7, 13, 14, 3, 0, 6, 9, 10, 1, 2, 8, 5, 11, 12, 4, 15 },
{ 13, 8, 11, 5, 6, 15, 0, 3, 4, 7, 2, 12, 1, 10, 14, 9 },
{ 10, 6, 9, 0, 12, 11, 7, 13, 15, 1, 3, 14, 5, 2, 8, 4 },
{ 3, 15, 0, 6, 10, 1, 13, 8, 9, 4, 5, 11, 12, 7, 2, 14 }
},
{ { 2, 12, 4, 1, 7, 10, 11, 6, 8, 5, 3, 15, 13, 0, 14, 9 },
{ 14, 11, 2, 12, 4, 7, 13, 1, 5, 0, 15, 10, 3, 9, 8, 6 },
{ 4, 2, 1, 11, 10, 13, 7, 8, 15, 9, 12, 5, 6, 3, 0, 14 },
{ 11, 8, 12, 7, 1, 14, 2, 13, 6, 15, 0, 9, 10, 4, 5, 3 }
},
{ { 12, 1, 10, 15, 9, 2, 6, 8, 0, 13, 3, 4, 14, 7, 5, 11 },
{ 10, 15, 4, 2, 7, 12, 9, 5, 6, 1, 13, 14, 0, 11, 3, 8 },
{ 9, 14, 15, 5, 2, 8, 12, 3, 7, 0, 4, 10, 1, 13, 11, 6 },
{ 4, 3, 2, 12, 9, 5, 15, 10, 11, 14, 1, 7, 6, 0, 8, 13 }
},
{ { 4, 11, 2, 14, 15, 0, 8, 13, 3, 12, 9, 7, 5, 10, 6, 1 },
{ 13, 0, 11, 7, 4, 9, 1, 10, 14, 3, 5, 12, 2, 15, 8, 6 },
{ 1, 4, 11, 13, 12, 3, 7, 14, 10, 15, 6, 8, 0, 5, 9, 2 },
{ 6, 11, 13, 8, 1, 4, 10, 7, 9, 5, 0, 15, 14, 2, 3, 12 }
},
{ { 13, 2, 8, 4, 6, 15, 11, 1, 10, 9, 3, 14, 5, 0, 12, 7 },
{ 1, 15, 13, 8, 10, 3, 7, 4, 12, 5, 6, 11, 0, 14, 9, 2 },
{ 7, 11, 4, 1, 9, 12, 14, 2, 0, 6, 10, 13, 15, 3, 5, 8 },
{ 2, 1, 14, 7, 4, 10, 8, 13, 15, 12, 9, 0, 3, 5, 6, 11 }
}
};
/*
* This is the final
* permutation matrix
*/
static int final_perm[64] = {
40, 8, 48, 16, 56, 24, 64, 32, 39, 7, 47, 15, 55, 23, 63, 31,
38, 6, 46, 14, 54, 22, 62, 30, 37, 5, 45, 13, 53, 21, 61, 29,
36, 4, 44, 12, 52, 20, 60, 28, 35, 3, 43, 11, 51, 19, 59, 27,
34, 2, 42, 10, 50, 18, 58, 26, 33, 1, 41, 9, 49, 17, 57, 25
};
/*
* The 16 DES keys in BITMASK format
*/
#ifdef _UFC_32_
long32 _ufc_keytab[16][2];
#endif
#ifdef _UFC_64_
long64 _ufc_keytab[16];
#endif
#define ascii_to_bin(c) ((c)>='a'?(c-59):(c)>='A'?((c)-53):(c)-'.')
#define bin_to_ascii(c) ((c)>=38?((c)-38+'a'):(c)>=12?((c)-12+'A'):(c)+'.')
/* Macro to set a bit (0..23) */
#define BITMASK(i) ( (1<<(11-(i)%12+3)) << ((i)<12?16:0) )
/*
* sb arrays:
*
* Workhorses of the inner loop of the DES implementation.
* They do sbox lookup, shifting of this value, 32 bit
* permutation and E permutation for the next round.
*
* Kept in 'BITMASK' format.
*/
#ifdef _UFC_32_
long32 _ufc_sb0[8192], _ufc_sb1[8192], _ufc_sb2[8192], _ufc_sb3[8192];
static long32 *sb[4] = {_ufc_sb0, _ufc_sb1, _ufc_sb2, _ufc_sb3};
#endif
#ifdef _UFC_64_
long64 _ufc_sb0[4096], _ufc_sb1[4096], _ufc_sb2[4096], _ufc_sb3[4096];
static long64 *sb[4] = {_ufc_sb0, _ufc_sb1, _ufc_sb2, _ufc_sb3};
#endif
/*
* eperm32tab: do 32 bit permutation and E selection
*
* The first index is the byte number in the 32 bit value to be permuted
* - second - is the value of this byte
* - third - selects the two 32 bit values
*
* The table is used and generated internally in init_des to speed it up
*/
static ufc_long eperm32tab[4][256][2];
/*
* do_pc1: permform pc1 permutation in the key schedule generation.
*
* The first index is the byte number in the 8 byte ASCII key
* - second - - the two 28 bits halfs of the result
* - third - selects the 7 bits actually used of each byte
*
* The result is kept with 28 bit per 32 bit with the 4 most significant
* bits zero.
*/
static ufc_long do_pc1[8][2][128];
/*
* do_pc2: permform pc2 permutation in the key schedule generation.
*
* The first index is the septet number in the two 28 bit intermediate values
* - second - - - septet values
*
* Knowledge of the structure of the pc2 permutation is used.
*
* The result is kept with 28 bit per 32 bit with the 4 most significant
* bits zero.
*/
static ufc_long do_pc2[8][128];
/*
* efp: undo an extra e selection and do final
* permutation giving the DES result.
*
* Invoked 6 bit a time on two 48 bit values
* giving two 32 bit longs.
*/
static ufc_long efp[16][64][2];
static unsigned char bytemask[8] = {
0x80, 0x40, 0x20, 0x10, 0x08, 0x04, 0x02, 0x01
};
static ufc_long longmask[32] = {
0x80000000, 0x40000000, 0x20000000, 0x10000000,
0x08000000, 0x04000000, 0x02000000, 0x01000000,
0x00800000, 0x00400000, 0x00200000, 0x00100000,
0x00080000, 0x00040000, 0x00020000, 0x00010000,
0x00008000, 0x00004000, 0x00002000, 0x00001000,
0x00000800, 0x00000400, 0x00000200, 0x00000100,
0x00000080, 0x00000040, 0x00000020, 0x00000010,
0x00000008, 0x00000004, 0x00000002, 0x00000001
};
/*
* Silly rewrite of 'bzero'. I do so
* because some machines don't have
* bzero and some don't have memset.
*/
static void clearmem(char *start, int cnt)
{ while(cnt--)
*start++ = '\0';
}
static int initialized = 0;
/* lookup a 6 bit value in sbox */
#define s_lookup(i,s) sbox[(i)][(((s)>>4) & 0x2)|((s) & 0x1)][((s)>>1) & 0xf];
/*
* Initialize unit - may be invoked directly
* by fcrypt users.
*/
static void ufc_init_des(void)
{ int comes_from_bit;
int bit, sg;
ufc_long j;
ufc_long mask1, mask2;
/*
* Create the do_pc1 table used
* to affect pc1 permutation
* when generating keys
*/
for(bit = 0; bit < 56; bit++) {
comes_from_bit = pc1[bit] - 1;
mask1 = bytemask[comes_from_bit % 8 + 1];
mask2 = longmask[bit % 28 + 4];
for(j = 0; j < 128; j++) {
if(j & mask1)
do_pc1[comes_from_bit / 8][bit / 28][j] |= mask2;
}
}
/*
* Create the do_pc2 table used
* to affect pc2 permutation when
* generating keys
*/
for(bit = 0; bit < 48; bit++) {
comes_from_bit = pc2[bit] - 1;
mask1 = bytemask[comes_from_bit % 7 + 1];
mask2 = BITMASK(bit % 24);
for(j = 0; j < 128; j++) {
if(j & mask1)
do_pc2[comes_from_bit / 7][j] |= mask2;
}
}
/*
* Now generate the table used to do combined
* 32 bit permutation and e expansion
*
* We use it because we have to permute 16384 32 bit
* longs into 48 bit in order to initialize sb.
*
* Looping 48 rounds per permutation becomes
* just too slow...
*
*/
clearmem((char*)eperm32tab, sizeof(eperm32tab));
for(bit = 0; bit < 48; bit++) {
ufc_long inner_mask1,comes_from;
comes_from = perm32[esel[bit]-1]-1;
inner_mask1 = bytemask[comes_from % 8];
for(j = 256; j--;) {
if(j & inner_mask1)
eperm32tab[comes_from / 8][j][bit / 24] |= BITMASK(bit % 24);
}
}
/*
* Create the sb tables:
*
* For each 12 bit segment of an 48 bit intermediate
* result, the sb table precomputes the two 4 bit
* values of the sbox lookups done with the two 6
* bit halves, shifts them to their proper place,
* sends them through perm32 and finally E expands
* them so that they are ready for the next
* DES round.
*
*/
for(sg = 0; sg < 4; sg++) {
int j1, j2;
int s1, s2;
for(j1 = 0; j1 < 64; j1++) {
s1 = s_lookup(2 * sg, j1);
for(j2 = 0; j2 < 64; j2++) {
ufc_long to_permute, inx;
s2 = s_lookup(2 * sg + 1, j2);
to_permute = ((s1 << 4) | s2) << (24 - 8 * sg);
#ifdef _UFC_32_
inx = ((j1 << 6) | j2) << 1;
sb[sg][inx ] = eperm32tab[0][(to_permute >> 24) & 0xff][0];
sb[sg][inx+1] = eperm32tab[0][(to_permute >> 24) & 0xff][1];
sb[sg][inx ] |= eperm32tab[1][(to_permute >> 16) & 0xff][0];
sb[sg][inx+1] |= eperm32tab[1][(to_permute >> 16) & 0xff][1];
sb[sg][inx ] |= eperm32tab[2][(to_permute >> 8) & 0xff][0];
sb[sg][inx+1] |= eperm32tab[2][(to_permute >> 8) & 0xff][1];
sb[sg][inx ] |= eperm32tab[3][(to_permute) & 0xff][0];
sb[sg][inx+1] |= eperm32tab[3][(to_permute) & 0xff][1];
#endif
#ifdef _UFC_64_
inx = ((j1 << 6) | j2);
sb[sg][inx] =
((long64)eperm32tab[0][(to_permute >> 24) & 0xff][0] << 32) |
(long64)eperm32tab[0][(to_permute >> 24) & 0xff][1];
sb[sg][inx] |=
((long64)eperm32tab[1][(to_permute >> 16) & 0xff][0] << 32) |
(long64)eperm32tab[1][(to_permute >> 16) & 0xff][1];
sb[sg][inx] |=
((long64)eperm32tab[2][(to_permute >> 8) & 0xff][0] << 32) |
(long64)eperm32tab[2][(to_permute >> 8) & 0xff][1];
sb[sg][inx] |=
((long64)eperm32tab[3][(to_permute) & 0xff][0] << 32) |
(long64)eperm32tab[3][(to_permute) & 0xff][1];
#endif
}
}
}
/*
* Create an inverse matrix for esel telling
* where to plug out bits if undoing it
*/
for(bit=48; bit--;) {
e_inverse[esel[bit] - 1 ] = bit;
e_inverse[esel[bit] - 1 + 32] = bit + 48;
}
/*
* create efp: the matrix used to
* undo the E expansion and effect final permutation
*/
clearmem((char*)efp, sizeof efp);
for(bit = 0; bit < 64; bit++) {
int o_bit, o_long;
ufc_long word_value, inner_mask1, inner_mask2;
int comes_from_f_bit, comes_from_e_bit;
int comes_from_word, bit_within_word;
/* See where bit i belongs in the two 32 bit long's */
o_long = bit / 32; /* 0..1 */
o_bit = bit % 32; /* 0..31 */
/*
* And find a bit in the e permutated value setting this bit.
*
* Note: the e selection may have selected the same bit several
* times. By the initialization of e_inverse, we only look
* for one specific instance.
*/
comes_from_f_bit = final_perm[bit] - 1; /* 0..63 */
comes_from_e_bit = e_inverse[comes_from_f_bit]; /* 0..95 */
comes_from_word = comes_from_e_bit / 6; /* 0..15 */
bit_within_word = comes_from_e_bit % 6; /* 0..5 */
inner_mask1 = longmask[bit_within_word + 26];
inner_mask2 = longmask[o_bit];
for(word_value = 64; word_value--;) {
if(word_value & inner_mask1)
efp[comes_from_word][word_value][o_long] |= inner_mask2;
}
}
initialized++;
}
/*
* Process the elements of the sb table permuting the
* bits swapped in the expansion by the current salt.
*/
#ifdef _UFC_32_
static void shuffle_sb(long32 *k, ufc_long saltbits)
{ ufc_long j;
long32 x;
for(j=4096; j--;) {
x = (k[0] ^ k[1]) & (long32)saltbits;
*k++ ^= x;
*k++ ^= x;
}
}
#endif
#ifdef _UFC_64_
static void shuffle_sb(long64 *k, ufc_long saltbits)
{ ufc_long j;
long64 x;
for(j=4096; j--;) {
x = ((*k >> 32) ^ *k) & (long64)saltbits;
*k++ ^= (x << 32) | x;
}
}
#endif
/*
* Setup the unit for a new salt
* Hopefully we'll not see a new salt in each crypt call.
*/
static unsigned char current_salt[3] = "&&"; /* invalid value */
static ufc_long current_saltbits = 0;
static int direction = 0;
static void setup_salt(const char *s1)
{ ufc_long i, j, saltbits;
const unsigned char *s2 = (const unsigned char *)s1;
if(!initialized)
ufc_init_des();
if(s2[0] == current_salt[0] && s2[1] == current_salt[1])
return;
current_salt[0] = s2[0]; current_salt[1] = s2[1];
/*
* This is the only crypt change to DES:
* entries are swapped in the expansion table
* according to the bits set in the salt.
*/
saltbits = 0;
for(i = 0; i < 2; i++) {
long c=ascii_to_bin(s2[i]);
if(c < 0 || c > 63)
c = 0;
for(j = 0; j < 6; j++) {
if((c >> j) & 0x1)
saltbits |= BITMASK(6 * i + j);
}
}
/*
* Permute the sb table values
* to reflect the changed e
* selection table
*/
shuffle_sb(_ufc_sb0, current_saltbits ^ saltbits);
shuffle_sb(_ufc_sb1, current_saltbits ^ saltbits);
shuffle_sb(_ufc_sb2, current_saltbits ^ saltbits);
shuffle_sb(_ufc_sb3, current_saltbits ^ saltbits);
current_saltbits = saltbits;
}
static void ufc_mk_keytab(char *key)
{ ufc_long v1, v2, *k1;
int i;
#ifdef _UFC_32_
long32 v, *k2 = &_ufc_keytab[0][0];
#endif
#ifdef _UFC_64_
long64 v, *k2 = &_ufc_keytab[0];
#endif
v1 = v2 = 0; k1 = &do_pc1[0][0][0];
for(i = 8; i--;) {
v1 |= k1[*key & 0x7f]; k1 += 128;
v2 |= k1[*key++ & 0x7f]; k1 += 128;
}
for(i = 0; i < 16; i++) {
k1 = &do_pc2[0][0];
v1 = (v1 << rots[i]) | (v1 >> (28 - rots[i]));
v = k1[(v1 >> 21) & 0x7f]; k1 += 128;
v |= k1[(v1 >> 14) & 0x7f]; k1 += 128;
v |= k1[(v1 >> 7) & 0x7f]; k1 += 128;
v |= k1[(v1 ) & 0x7f]; k1 += 128;
#ifdef _UFC_32_
*k2++ = v;
v = 0;
#endif
#ifdef _UFC_64_
v <<= 32;
#endif
v2 = (v2 << rots[i]) | (v2 >> (28 - rots[i]));
v |= k1[(v2 >> 21) & 0x7f]; k1 += 128;
v |= k1[(v2 >> 14) & 0x7f]; k1 += 128;
v |= k1[(v2 >> 7) & 0x7f]; k1 += 128;
v |= k1[(v2 ) & 0x7f];
*k2++ = v;
}
direction = 0;
}
/*
* Undo an extra E selection and do final permutations
*/
ufc_long *_ufc_dofinalperm(ufc_long l1, ufc_long l2, ufc_long r1, ufc_long r2)
{ ufc_long v1, v2, x;
static ufc_long ary[2];
x = (l1 ^ l2) & current_saltbits; l1 ^= x; l2 ^= x;
x = (r1 ^ r2) & current_saltbits; r1 ^= x; r2 ^= x;
v1=v2=0; l1 >>= 3; l2 >>= 3; r1 >>= 3; r2 >>= 3;
v1 |= efp[15][ r2 & 0x3f][0]; v2 |= efp[15][ r2 & 0x3f][1];
v1 |= efp[14][(r2 >>= 6) & 0x3f][0]; v2 |= efp[14][ r2 & 0x3f][1];
v1 |= efp[13][(r2 >>= 10) & 0x3f][0]; v2 |= efp[13][ r2 & 0x3f][1];
v1 |= efp[12][(r2 >>= 6) & 0x3f][0]; v2 |= efp[12][ r2 & 0x3f][1];
v1 |= efp[11][ r1 & 0x3f][0]; v2 |= efp[11][ r1 & 0x3f][1];
v1 |= efp[10][(r1 >>= 6) & 0x3f][0]; v2 |= efp[10][ r1 & 0x3f][1];
v1 |= efp[ 9][(r1 >>= 10) & 0x3f][0]; v2 |= efp[ 9][ r1 & 0x3f][1];
v1 |= efp[ 8][(r1 >>= 6) & 0x3f][0]; v2 |= efp[ 8][ r1 & 0x3f][1];
v1 |= efp[ 7][ l2 & 0x3f][0]; v2 |= efp[ 7][ l2 & 0x3f][1];
v1 |= efp[ 6][(l2 >>= 6) & 0x3f][0]; v2 |= efp[ 6][ l2 & 0x3f][1];
v1 |= efp[ 5][(l2 >>= 10) & 0x3f][0]; v2 |= efp[ 5][ l2 & 0x3f][1];
v1 |= efp[ 4][(l2 >>= 6) & 0x3f][0]; v2 |= efp[ 4][ l2 & 0x3f][1];
v1 |= efp[ 3][ l1 & 0x3f][0]; v2 |= efp[ 3][ l1 & 0x3f][1];
v1 |= efp[ 2][(l1 >>= 6) & 0x3f][0]; v2 |= efp[ 2][ l1 & 0x3f][1];
v1 |= efp[ 1][(l1 >>= 10) & 0x3f][0]; v2 |= efp[ 1][ l1 & 0x3f][1];
v1 |= efp[ 0][(l1 >>= 6) & 0x3f][0]; v2 |= efp[ 0][ l1 & 0x3f][1];
ary[0] = v1; ary[1] = v2;
return ary;
}
/*
* crypt only: convert from 64 bit to 11 bit ASCII
* prefixing with the salt
*/
static char *output_conversion(ufc_long v1, ufc_long v2, const char *salt)
{ static char outbuf[14];
int i, s;
outbuf[0] = salt[0];
outbuf[1] = salt[1] ? salt[1] : salt[0];
for(i = 0; i < 5; i++)
outbuf[i + 2] = bin_to_ascii((v1 >> (26 - 6 * i)) & 0x3f);
s = (v2 & 0xf) << 2;
v2 = (v2 >> 2) | ((v1 & 0x3) << 30);
for(i = 5; i < 10; i++)
outbuf[i + 2] = bin_to_ascii((v2 >> (56 - 6 * i)) & 0x3f);
outbuf[12] = bin_to_ascii(s);
outbuf[13] = 0;
return outbuf;
}
/*
* UNIX crypt function
*/
static ufc_long *_ufc_doit(ufc_long , ufc_long, ufc_long, ufc_long, ufc_long);
char *ufc_crypt(const char *key,const char *salt)
{ ufc_long *s;
char ktab[9];
/*
* Hack DES tables according to salt
*/
setup_salt(salt);
/*
* Setup key schedule
*/
clearmem(ktab, sizeof ktab);
strncpy(ktab, key, 8);
ufc_mk_keytab(ktab);
/*
* Go for the 25 DES encryptions
*/
s = _ufc_doit((ufc_long)0, (ufc_long)0,
(ufc_long)0, (ufc_long)0, (ufc_long)25);
/*
* And convert back to 6 bit ASCII
*/
return output_conversion(s[0], s[1], salt);
}
#ifdef _UFC_32_
/*
* 32 bit version
*/
extern long32 _ufc_keytab[16][2];
extern long32 _ufc_sb0[], _ufc_sb1[], _ufc_sb2[], _ufc_sb3[];
#define SBA(sb, v) (*(long32*)((char*)(sb)+(v)))
static ufc_long *_ufc_doit(ufc_long l1, ufc_long l2, ufc_long r1, ufc_long r2, ufc_long itr)
{ int i;
long32 s, *k;
while(itr--) {
k = &_ufc_keytab[0][0];
for(i=8; i--; ) {
s = *k++ ^ r1;
l1 ^= SBA(_ufc_sb1, s & 0xffff); l2 ^= SBA(_ufc_sb1, (s & 0xffff)+4);
l1 ^= SBA(_ufc_sb0, s >>= 16); l2 ^= SBA(_ufc_sb0, (s) +4);
s = *k++ ^ r2;
l1 ^= SBA(_ufc_sb3, s & 0xffff); l2 ^= SBA(_ufc_sb3, (s & 0xffff)+4);
l1 ^= SBA(_ufc_sb2, s >>= 16); l2 ^= SBA(_ufc_sb2, (s) +4);
s = *k++ ^ l1;
r1 ^= SBA(_ufc_sb1, s & 0xffff); r2 ^= SBA(_ufc_sb1, (s & 0xffff)+4);
r1 ^= SBA(_ufc_sb0, s >>= 16); r2 ^= SBA(_ufc_sb0, (s) +4);
s = *k++ ^ l2;
r1 ^= SBA(_ufc_sb3, s & 0xffff); r2 ^= SBA(_ufc_sb3, (s & 0xffff)+4);
r1 ^= SBA(_ufc_sb2, s >>= 16); r2 ^= SBA(_ufc_sb2, (s) +4);
}
s=l1; l1=r1; r1=s; s=l2; l2=r2; r2=s;
}
return _ufc_dofinalperm(l1, l2, r1, r2);
}
#endif
#ifdef _UFC_64_
/*
* 64 bit version
*/
extern long64 _ufc_keytab[16];
extern long64 _ufc_sb0[], _ufc_sb1[], _ufc_sb2[], _ufc_sb3[];
#define SBA(sb, v) (*(long64*)((char*)(sb)+(v)))
static ufc_long *_ufc_doit(ufc_long l1, ufc_long l2, ufc_long r1, ufc_long r2, ufc_long itr)
{ int i;
long64 l, r, s, *k;
l = (((long64)l1) << 32) | ((long64)l2);
r = (((long64)r1) << 32) | ((long64)r2);
while(itr--) {
k = &_ufc_keytab[0];
for(i=8; i--; ) {
s = *k++ ^ r;
l ^= SBA(_ufc_sb3, (s >> 0) & 0xffff);
l ^= SBA(_ufc_sb2, (s >> 16) & 0xffff);
l ^= SBA(_ufc_sb1, (s >> 32) & 0xffff);
l ^= SBA(_ufc_sb0, (s >> 48) & 0xffff);
s = *k++ ^ l;
r ^= SBA(_ufc_sb3, (s >> 0) & 0xffff);
r ^= SBA(_ufc_sb2, (s >> 16) & 0xffff);
r ^= SBA(_ufc_sb1, (s >> 32) & 0xffff);
r ^= SBA(_ufc_sb0, (s >> 48) & 0xffff);
}
s=l; l=r; r=s;
}
l1 = l >> 32; l2 = l & 0xffffffff;
r1 = r >> 32; r2 = r & 0xffffffff;
return _ufc_dofinalperm(l1, l2, r1, r2);
}
#endif
#define crypt ufc_crypt
#endif
main()
{
char passwd[9];
char salt[9];
char c_out1[256];
char c_out2[256];
char expected_out[14];
strcpy(expected_out, "12yJ.Of/NQ.Pk");
strcpy(passwd, "12345678");
strcpy(salt, "12345678");
strcpy(c_out1, crypt(passwd, salt));
salt[2] = '\0';
strcpy(c_out2, crypt(passwd, salt));
/*
* If the non-trucated salt fails but the
* truncated salt succeeds then exit 1.
*/
if((strcmp(c_out1, expected_out) != 0) &&
(strcmp(c_out2, expected_out) == 0))
exit(1);
#ifdef HAVE_BIGCRYPT
/*
* Try the same with bigcrypt...
*/
{
char big_passwd[17];
char big_salt[17];
char big_c_out1[256];
char big_c_out2[256];
char big_expected_out[27];
strcpy(big_passwd, "1234567812345678");
strcpy(big_salt, "1234567812345678");
strcpy(big_expected_out, "12yJ.Of/NQ.PklfyCuHi/rwM");
strcpy(big_c_out1, bigcrypt(big_passwd, big_salt));
big_salt[2] = '\0';
strcpy(big_c_out2, bigcrypt(big_passwd, big_salt));
/*
* If the non-trucated salt fails but the
* truncated salt succeeds then exit 1.
*/
if((strcmp(big_c_out1, big_expected_out) != 0) &&
(strcmp(big_c_out2, big_expected_out) == 0))
exit(1);
}
#endif
exit(0);
}

View File

@ -0,0 +1,121 @@
/* test whether fcntl locking works on this system */
#if defined(HAVE_UNISTD_H)
#include <unistd.h>
#endif
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#ifdef HAVE_FCNTL_H
#include <fcntl.h>
#endif
#ifdef HAVE_SYS_FCNTL_H
#include <sys/fcntl.h>
#endif
#ifdef HAVE_SYS_WAIT_H
#include <sys/wait.h>
#endif
#include <errno.h>
static int sys_waitpid(pid_t pid,int *status,int options)
{
#ifdef HAVE_WAITPID
return waitpid(pid,status,options);
#else /* USE_WAITPID */
return wait4(pid, status, options, NULL);
#endif /* USE_WAITPID */
}
#define DATA "conftest.fcntl"
#ifndef SEEK_SET
#define SEEK_SET 0
#endif
/* lock a byte range in a open file */
int main(int argc, char *argv[])
{
struct flock lock;
int fd, ret, status=1;
pid_t pid;
char *testdir = NULL;
testdir = getenv("TESTDIR");
if (testdir) chdir(testdir);
alarm(10);
if (!(pid=fork())) {
sleep(2);
fd = open(DATA, O_RDONLY);
if (fd == -1) {
fprintf(stderr,"ERROR: failed to open %s (errno=%d)\n",
DATA, (int)errno);
exit(1);
}
lock.l_type = F_WRLCK;
lock.l_whence = SEEK_SET;
lock.l_start = 0;
lock.l_len = 4;
lock.l_pid = getpid();
lock.l_type = F_WRLCK;
/* check if a lock applies */
ret = fcntl(fd,F_GETLK,&lock);
if ((ret == -1) ||
(lock.l_type == F_UNLCK)) {
fprintf(stderr,"ERROR: lock test failed (ret=%d errno=%d)\n", ret, (int)errno);
exit(1);
} else {
exit(0);
}
}
unlink(DATA);
fd = open(DATA, O_RDWR|O_CREAT|O_EXCL, 0600);
if (fd == -1) {
fprintf(stderr,"ERROR: failed to open %s (errno=%d)\n",
DATA, (int)errno);
exit(1);
}
lock.l_type = F_WRLCK;
lock.l_whence = SEEK_SET;
lock.l_start = 0;
lock.l_len = 4;
lock.l_pid = getpid();
/* set a 4 byte write lock */
fcntl(fd,F_SETLK,&lock);
sys_waitpid(pid, &status, 0);
unlink(DATA);
#if defined(WIFEXITED) && defined(WEXITSTATUS)
if(WIFEXITED(status)) {
status = WEXITSTATUS(status);
} else {
status = 1;
}
#else /* defined(WIFEXITED) && defined(WEXITSTATUS) */
status = (status == 0) ? 0 : 1;
#endif /* defined(WIFEXITED) && defined(WEXITSTATUS) */
if (status) {
fprintf(stderr,"ERROR: lock test failed with status=%d\n",
status);
}
exit(status);
}

View File

@ -0,0 +1,96 @@
/* test whether 64 bit fcntl locking really works on this system */
#if defined(HAVE_UNISTD_H)
#include <unistd.h>
#endif
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#ifdef HAVE_FCNTL_H
#include <fcntl.h>
#endif
#ifdef HAVE_SYS_FCNTL_H
#include <sys/fcntl.h>
#endif
#include <errno.h>
static int sys_waitpid(pid_t pid,int *status,int options)
{
#ifdef HAVE_WAITPID
return waitpid(pid,status,options);
#else /* USE_WAITPID */
return wait4(pid, status, options, NULL);
#endif /* USE_WAITPID */
}
#define DATA "conftest.fcntl64"
/* lock a byte range in a open file */
int main(int argc, char *argv[])
{
struct flock64 lock;
int fd, ret, status=1;
pid_t pid;
if (!(pid=fork())) {
sleep(2);
fd = open64(DATA, O_RDONLY);
if (fd == -1) exit(1);
lock.l_type = F_WRLCK;
lock.l_whence = SEEK_SET;
lock.l_start = 0;
lock.l_len = 4;
lock.l_pid = getpid();
lock.l_type = F_WRLCK;
/* check if a lock applies */
ret = fcntl(fd,F_GETLK64,&lock);
if ((ret == -1) ||
(lock.l_type == F_UNLCK)) {
/* printf("No lock conflict\n"); */
exit(1);
} else {
/* printf("lock conflict\n"); */
exit(0);
}
}
fd = open64(DATA, O_RDWR|O_CREAT|O_TRUNC, 0600);
lock.l_type = F_WRLCK;
lock.l_whence = SEEK_SET;
#if defined(COMPILER_SUPPORTS_LL)
lock.l_start = 0x100000000LL;
#else
lock.l_start = 0x100000000;
#endif
lock.l_len = 4;
lock.l_pid = getpid();
/* set a 4 byte write lock */
fcntl(fd,F_SETLK64,&lock);
sys_waitpid(pid, &status, 0);
#if defined(WIFEXITED) && defined(WEXITSTATUS)
if(WIFEXITED(status)) {
status = WEXITSTATUS(status);
} else {
status = 1;
}
#else /* defined(WIFEXITED) && defined(WEXITSTATUS) */
status = (status == 0) ? 0 : 1;
#endif /* defined(WIFEXITED) && defined(WEXITSTATUS) */
unlink(DATA);
exit(status);
}

View File

@ -0,0 +1,122 @@
/* test whether fcntl locking works between threads on this Linux system */
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
#include <sys/types.h>
#include <fcntl.h>
#include <sys/fcntl.h>
#include <sys/wait.h>
#include <errno.h>
#include <pthread.h>
static int sys_waitpid(pid_t pid,int *status,int options)
{
return waitpid(pid,status,options);
}
#define DATA "conftest.fcntl"
#define SEEK_SET 0
static void *test_thread(void *thread_parm)
{
int *status = thread_parm;
int fd, ret;
struct flock lock;
sleep(2);
fd = open(DATA, O_RDWR);
if (fd == -1) {
fprintf(stderr,"ERROR: failed to open %s (errno=%d)\n",
DATA, (int)errno);
pthread_exit(thread_parm);
}
lock.l_type = F_WRLCK;
lock.l_whence = SEEK_SET;
lock.l_start = 0;
lock.l_len = 4;
lock.l_pid = 0;
/* check if a lock applies */
ret = fcntl(fd,F_SETLK,&lock);
if ((ret != -1)) {
fprintf(stderr,"ERROR: lock test failed (ret=%d errno=%d)\n", ret, (int)errno);
} else {
*status = 0; /* SUCCESS! */
}
pthread_exit(thread_parm);
}
/* lock a byte range in a open file */
int main(int argc, char *argv[])
{
struct flock lock;
int fd, ret, status=1, rc;
pid_t pid;
char *testdir = NULL;
pthread_t thread_id;
pthread_attr_t thread_attr;
testdir = getenv("TESTDIR");
if (testdir) chdir(testdir);
alarm(10);
pthread_attr_init(&thread_attr);
pthread_attr_setdetachstate(&thread_attr, PTHREAD_CREATE_DETACHED);
rc = pthread_create(&thread_id, &thread_attr, &test_thread, &status);
pthread_attr_destroy(&thread_attr);
if (rc == 0) {
fprintf(stderr,"created thread_id=%lu\n",
(unsigned long int)thread_id);
} else {
fprintf(stderr,"ERROR: thread create failed, rc=%d\n", rc);
}
unlink(DATA);
fd = open(DATA, O_RDWR|O_CREAT|O_RDWR, 0600);
if (fd == -1) {
fprintf(stderr,"ERROR: failed to open %s (errno=%d)\n",
DATA, (int)errno);
exit(1);
}
lock.l_type = F_WRLCK;
lock.l_whence = SEEK_SET;
lock.l_start = 0;
lock.l_len = 4;
lock.l_pid = getpid();
/* set a 4 byte write lock */
fcntl(fd,F_SETLK,&lock);
sleep(4); /* allow thread to try getting lock */
unlink(DATA);
#if defined(WIFEXITED) && defined(WEXITSTATUS)
if(WIFEXITED(status)) {
status = WEXITSTATUS(status);
} else {
status = 1;
}
#else /* defined(WIFEXITED) && defined(WEXITSTATUS) */
status = (status == 0) ? 0 : 1;
#endif /* defined(WIFEXITED) && defined(WEXITSTATUS) */
if (status) {
fprintf(stderr,"ERROR: lock test failed with status=%d\n",
status);
}
exit(status);
}

View File

@ -0,0 +1,27 @@
/* test whether ftruncte() can extend a file */
#if defined(HAVE_UNISTD_H)
#include <unistd.h>
#endif
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#define DATA "conftest.trunc"
#define LEN 7663
main()
{
int *buf;
int fd = open(DATA,O_RDWR|O_CREAT|O_TRUNC,0666);
ftruncate(fd, LEN);
unlink(DATA);
if (lseek(fd, 0, SEEK_END) == LEN) {
exit(0);
}
exit(1);
}

View File

@ -0,0 +1,66 @@
/* this tests whether getgroups actually returns lists of integers
rather than gid_t. The test only works if the user running
the test is in at least 1 group
The test is designed to check for those broken OSes that define
getgroups() as returning an array of gid_t but actually return a
array of ints! Ultrix is one culprit
*/
#if defined(HAVE_UNISTD_H)
#include <unistd.h>
#endif
#include <sys/types.h>
#include <stdio.h>
#include <unistd.h>
#include <grp.h>
main()
{
int i;
int *igroups;
char *cgroups;
int grp = 0;
int ngroups = getgroups(0,&grp);
if (sizeof(gid_t) == sizeof(int)) {
fprintf(stderr,"gid_t and int are the same size\n");
exit(1);
}
if (ngroups <= 0)
ngroups = 32;
igroups = (int *)malloc(sizeof(int)*ngroups);
for (i=0;i<ngroups;i++)
igroups[i] = 0x42424242;
ngroups = getgroups(ngroups,(gid_t *)igroups);
if (igroups[0] == 0x42424242)
ngroups = 0;
if (ngroups == 0) {
printf("WARNING: can't determine getgroups return type\n");
exit(1);
}
cgroups = (char *)igroups;
if (ngroups == 1 &&
cgroups[2] == 0x42 && cgroups[3] == 0x42) {
fprintf(stderr,"getgroups returns gid_t\n");
exit(1);
}
for (i=0;i<ngroups;i++) {
if (igroups[i] == 0x42424242) {
fprintf(stderr,"getgroups returns gid_t\n");
exit(1);
}
}
exit(0);
}

View File

@ -0,0 +1,68 @@
/* this tests whether we can use a shared writeable mmap on a file -
as needed for the mmap varient of FAST_SHARE_MODES */
#if defined(HAVE_UNISTD_H)
#include <unistd.h>
#endif
#include <sys/mman.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#define DATA "conftest.mmap"
#ifndef MAP_FILE
#define MAP_FILE 0
#endif
main()
{
int *buf;
int i;
int fd = open(DATA,O_RDWR|O_CREAT|O_TRUNC,0666);
int count=7;
if (fd == -1) exit(1);
for (i=0;i<10000;i++) {
write(fd,&i,sizeof(i));
}
close(fd);
if (fork() == 0) {
fd = open(DATA,O_RDWR);
if (fd == -1) exit(1);
buf = (int *)mmap(NULL, 10000*sizeof(int),
(PROT_READ | PROT_WRITE),
MAP_FILE | MAP_SHARED,
fd, 0);
while (count-- && buf[9124] != 55732) sleep(1);
if (count <= 0) exit(1);
buf[1763] = 7268;
exit(0);
}
fd = open(DATA,O_RDWR);
if (fd == -1) exit(1);
buf = (int *)mmap(NULL, 10000*sizeof(int),
(PROT_READ | PROT_WRITE),
MAP_FILE | MAP_SHARED,
fd, 0);
if (buf == (int *)-1) exit(1);
buf[9124] = 55732;
while (count-- && buf[1763] != 7268) sleep(1);
unlink(DATA);
if (count > 0) exit(0);
exit(1);
}

View File

@ -0,0 +1,6 @@
/* a trivial function used to test building shared libraries */
int foo(void)
{
return 1;
}

View File

@ -0,0 +1,30 @@
#include <stdio.h>
main()
{
#if !(defined(HAVE_FCNTL_LOCK) || defined(HAVE_STRUCT_FLOCK64))
printf("ERROR: No locking available. Running Samba would be unsafe\n");
exit(1);
#endif
#if !(defined(HAVE_IFACE_IFCONF) || defined(HAVE_IFACE_IFREQ) || defined(HAVE_IFACE_AIX))
printf("WARNING: No automated network interface determination\n");
#endif
#if !(defined(USE_SETEUID) || defined(USE_SETREUID) || defined(USE_SETRESUID) || defined(USE_SETUIDX))
printf("ERROR: no seteuid method available\n");
/* REWRITE: exit(1); */
#endif
#if !(defined(STAT_STATVFS) || defined(STAT_STATVFS64) || defined(STAT_STATFS3_OSF1) || defined(STAT_STATFS2_BSIZE) || defined(STAT_STATFS4) || defined(STAT_STATFS2_FSIZE) || defined(STAT_STATFS2_FS_DATA))
printf("ERROR: No disk free routine!\n");
exit(1);
#endif
#if !((defined(HAVE_RANDOM) || defined(HAVE_RAND)) && (defined(HAVE_SRANDOM) || defined(HAVE_SRAND)))
printf("ERROR: No random or srandom routine!\n");
exit(1);
#endif
exit(0);
}

View File

@ -0,0 +1,4 @@
main()
{
exit(0);
}

View File

@ -0,0 +1,93 @@
/* -*- c-file-style: "linux" -*-
*
* Try creating a Unix-domain socket, opening it, and reading from it.
* The POSIX name for these is AF_LOCAL/PF_LOCAL.
*
* This is used by the Samba autoconf scripts to detect systems which
* don't have Unix-domain sockets, such as (probably) VMS, or systems
* on which they are broken under some conditions, such as RedHat 7.0
* (unpatched). We can't build WinBind there at the moment.
*
* Coding standard says to always use exit() for this, not return, so
* we do.
*
* Martin Pool <mbp@samba.org>, June 2000. */
/* TODO: Look for AF_LOCAL (most standard), AF_UNIX, and AF_FILE. */
#include <stdio.h>
#ifdef HAVE_SYS_SOCKET_H
# include <sys/socket.h>
#endif
#ifdef HAVE_SYS_UN_H
# include <sys/un.h>
#endif
#ifdef HAVE_SYS_TYPES_H
# include <sys/types.h>
#endif
#if HAVE_SYS_WAIT_H
# include <sys/wait.h>
#endif
#if HAVE_ERRNO_DECL
# include <errno.h>
#else
extern int errno;
#endif
static int bind_socket(char const *filename)
{
int sock_fd;
struct sockaddr_un name;
size_t size;
/* Create the socket. */
if ((sock_fd = socket(PF_LOCAL, SOCK_STREAM, 0)) < 0) {
perror ("socket(PF_LOCAL, SOCK_STREAM)");
exit(1);
}
/* Bind a name to the socket. */
name.sun_family = AF_LOCAL;
strncpy(name.sun_path, filename, sizeof (name.sun_path));
/* The size of the address is
the offset of the start of the filename,
plus its length,
plus one for the terminating null byte.
Alternatively you can just do:
size = SUN_LEN (&name);
*/
size = SUN_LEN(&name);
/* XXX: This probably won't work on unfriendly libcs */
if (bind(sock_fd, (struct sockaddr *) &name, size) < 0) {
perror ("bind");
exit(1);
}
return sock_fd;
}
int main(void)
{
int sock_fd;
int kid;
char const *filename = "conftest.unixsock.sock";
/* abolish hanging */
alarm(15); /* secs */
if ((sock_fd = bind_socket(filename)) < 0)
exit(1);
/* the socket will be deleted when autoconf cleans up these
files. */
exit(0);
}

1878
source4/change-log Normal file

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1 @@
client_proto.h

3025
source4/client/client.c Normal file

File diff suppressed because it is too large Load Diff

1856
source4/client/clitar.c Normal file

File diff suppressed because it is too large Load Diff

557
source4/client/mount.cifs.c Normal file
View File

@ -0,0 +1,557 @@
#define _GNU_SOURCE
#include <stdlib.h>
#include <unistd.h>
#include <pwd.h>
#include <sys/types.h>
#include <sys/mount.h>
#include <sys/stat.h>
#include <sys/utsname.h>
#include <sys/socket.h>
#include <arpa/inet.h>
#include <getopt.h>
#include <errno.h>
#include <netdb.h>
#include <string.h>
#include <mntent.h>
#define MOUNT_CIFS_VERSION "1"
extern char *getusername(void);
char * thisprogram;
int verboseflag = 0;
static int got_password = 0;
static int got_user = 0;
static int got_domain = 0;
static int got_ip = 0;
static int got_unc = 0;
static int got_uid = 0;
static int got_gid = 0;
static char * user_name = NULL;
char * mountpassword = NULL;
void mount_cifs_usage()
{
printf("\nUsage: %s remotetarget dir\n", thisprogram);
printf("\nMount the remotetarget, specified as either a UNC name or ");
printf(" CIFS URL, to the local directory, dir.\n");
exit(1);
}
/* caller frees username if necessary */
char * getusername() {
char *username = NULL;
struct passwd *password = getpwuid(getuid());
if (password) {
username = password->pw_name;
}
return username;
}
char * parse_cifs_url(unc_name)
{
printf("\ncifs url %s\n",unc_name);
}
int parse_options(char * options)
{
char * data;
char * value = 0;
if (!options)
return 1;
while ((data = strsep(&options, ",")) != NULL) {
if (!*data)
continue;
if ((value = strchr(data, '=')) != NULL) {
*value++ = '\0';
}
if (strncmp(data, "user", 4) == 0) {
if (!value || !*value) {
printf("invalid or missing username\n");
return 1; /* needs_arg; */
}
if (strnlen(value, 260) < 260) {
got_user=1;
/* BB add check for format user%pass */
/* if(strchr(username%passw) got_password = 1) */
} else {
printf("username too long\n");
return 1;
}
} else if (strncmp(data, "pass", 4) == 0) {
if (!value || !*value) {
if(got_password) {
printf("password specified twice, ignoring second\n");
} else
got_password = 1;
} else if (strnlen(value, 17) < 17) {
got_password = 1;
} else {
printf("password too long\n");
return 1;
}
} else if (strncmp(data, "ip", 2) == 0) {
if (!value || !*value) {
printf("target ip address argument missing");
} else if (strnlen(value, 35) < 35) {
got_ip = 1;
} else {
printf("ip address too long\n");
return 1;
}
} else if ((strncmp(data, "unc", 3) == 0)
|| (strncmp(data, "target", 6) == 0)
|| (strncmp(data, "path", 4) == 0)) {
if (!value || !*value) {
printf("invalid path to network resource\n");
return 1; /* needs_arg; */
} else if(strnlen(value,5) < 5) {
printf("UNC name too short");
}
if (strnlen(value, 300) < 300) {
got_unc = 1;
if (strncmp(value, "//", 2) == 0) {
if(got_unc)
printf("unc name specified twice, ignoring second\n");
else
got_unc = 1;
} else if (strncmp(value, "\\\\", 2) != 0) {
printf("UNC Path does not begin with // or \\\\ \n");
return 1;
} else {
if(got_unc)
printf("unc name specified twice, ignoring second\n");
else
got_unc = 1;
}
} else {
printf("CIFS: UNC name too long\n");
return 1;
}
} else if ((strncmp(data, "domain", 3) == 0)
|| (strncmp(data, "workgroup", 5) == 0)) {
if (!value || !*value) {
printf("CIFS: invalid domain name\n");
return 1; /* needs_arg; */
}
if (strnlen(value, 65) < 65) {
got_domain = 1;
} else {
printf("domain name too long\n");
return 1;
}
} else if (strncmp(data, "uid", 3) == 0) {
if (value && *value) {
got_uid = 1;
}
} else if (strncmp(data, "gid", 3) == 0) {
if (value && *value) {
got_gid = 1;
}
} /* else if (strnicmp(data, "file_mode", 4) == 0) {
if (value && *value) {
vol->file_mode =
simple_strtoul(value, &value, 0);
}
} else if (strnicmp(data, "dir_mode", 3) == 0) {
if (value && *value) {
vol->dir_mode =
simple_strtoul(value, &value, 0);
}
} else if (strnicmp(data, "port", 4) == 0) {
if (value && *value) {
vol->port =
simple_strtoul(value, &value, 0);
}
} else if (strnicmp(data, "rsize", 5) == 0) {
if (value && *value) {
vol->rsize =
simple_strtoul(value, &value, 0);
}
} else if (strnicmp(data, "wsize", 5) == 0) {
if (value && *value) {
vol->wsize =
simple_strtoul(value, &value, 0);
}
} else if (strnicmp(data, "version", 3) == 0) {
} else if (strnicmp(data, "rw", 2) == 0) {
} else
printf("CIFS: Unknown mount option %s\n",data); */
}
return 0;
}
/* Note that caller frees the returned buffer if necessary */
char * parse_server(char * unc_name)
{
int length = strnlen(unc_name,1024);
char * share;
char * ipaddress_string = NULL;
struct hostent * host_entry;
struct in_addr server_ipaddr;
int rc,j;
char temp[64];
if(length > 1023) {
printf("mount error: UNC name too long");
return 0;
}
if (strncasecmp("cifs://",unc_name,7) == 0)
return parse_cifs_url(unc_name+7);
if (strncasecmp("smb://",unc_name,6) == 0) {
return parse_cifs_url(unc_name+6);
}
if(length < 3) {
/* BB add code to find DFS root here */
printf("\nMounting the DFS root for domain not implemented yet");
return 0;
} else {
/* BB add support for \\\\ not just // */
if(strncmp(unc_name,"//",2) && strncmp(unc_name,"\\\\",2)) {
printf("mount error: improperly formatted UNC name.");
printf(" %s does not begin with \\\\ or //\n",unc_name);
return 0;
} else {
unc_name[0] = '\\';
unc_name[1] = '\\';
unc_name += 2;
if ((share = strchr(unc_name, '/')) ||
(share = strchr(unc_name,'\\'))) {
*share = 0; /* temporarily terminate the string */
share += 1;
host_entry = gethostbyname(unc_name);
*(share - 1) = '\\'; /* put the slash back */
/* rc = getipnodebyname(unc_name, AF_INET, AT_ADDRCONFIG ,&rc);*/
if(host_entry == NULL) {
printf("mount error: could not find target server. TCP name %s not found ", unc_name);
printf(" rc = %d\n",rc);
return 0;
}
else {
/* BB should we pass an alternate version of the share name as Unicode */
/* BB what about ipv6? BB */
/* BB add retries with alternate servers in list */
memcpy(&server_ipaddr.s_addr, host_entry->h_addr, 4);
ipaddress_string = inet_ntoa(server_ipaddr);
if(ipaddress_string == NULL) {
printf("mount error: could not get valid ip address for target server\n");
return 0;
}
return ipaddress_string;
}
} else {
/* BB add code to find DFS root (send null path on get DFS Referral to specified server here */
printf("Mounting the DFS root for a particular server not implemented yet\n");
return 0;
}
}
}
}
static struct option longopts[] = {
{ "all", 0, 0, 'a' },
{ "help", 0, 0, 'h' },
{ "read-only", 0, 0, 'r' },
{ "ro", 0, 0, 'r' },
{ "verbose", 0, 0, 'v' },
{ "version", 0, 0, 'V' },
{ "read-write", 0, 0, 'w' },
{ "rw", 0, 0, 'w' },
{ "options", 1, 0, 'o' },
{ "types", 1, 0, 't' },
{ "replace", 0, 0, 129 },
{ "after", 0, 0, 130 },
{ "before", 0, 0, 131 },
{ "over", 0, 0, 132 },
{ "move", 0, 0, 133 },
{ "rsize",1, 0, 136 },
{ "wsize",1, 0, 137 },
{ "uid", 1, 0, 138},
{ "gid", 1, 0, 139},
{ "uuid",1,0,'U' },
{ "user",1,0,140},
{ "username",1,0,140},
{ "dom",1,0,141},
{ "domain",1,0,141},
{ "password",1,0,142},
{ NULL, 0, 0, 0 }
};
int main(int argc, char ** argv)
{
int c;
int flags = MS_MANDLOCK | MS_MGC_VAL;
char * orgoptions = NULL;
char * share_name = NULL;
char * domain_name = NULL;
char * ipaddr = NULL;
char * uuid = NULL;
char * mountpoint;
char * options;
int rc,i;
int rsize = 0;
int wsize = 0;
int nomtab = 0;
int uid = 0;
int gid = 0;
int optlen = 0;
struct stat statbuf;
struct utsname sysinfo;
struct mntent mountent;
FILE * pmntfile;
/* setlocale(LC_ALL, "");
bindtextdomain(PACKAGE, LOCALEDIR);
textdomain(PACKAGE); */
if(argc && argv) {
thisprogram = argv[0];
}
if(thisprogram == NULL)
thisprogram = "mount.cifs";
uname(&sysinfo);
/* BB add workstation name and domain and pass down */
/*#ifdef _GNU_SOURCE
printf(" node: %s machine: %s\n", sysinfo.nodename,sysinfo.machine);
#endif*/
if(argc < 3)
mount_cifs_usage();
share_name = argv[1];
mountpoint = argv[2];
/* add sharename in opts string as unc= parm */
while ((c = getopt_long (argc, argv, "afFhilL:no:O:rsU:vVwt:",
longopts, NULL)) != -1) {
switch (c) {
/* case 'a':
++mount_all;
break;
case 'f':
++fake;
break;
case 'F':
++optfork;
break; */
case 'h': /* help */
mount_cifs_usage ();
break;
/* case 'i':
external_allowed = 0;
break;
case 'l':
list_with_volumelabel = 1;
break;
case 'L':
volumelabel = optarg;
break; */
case 'n':
++nomtab;
break;
case 'o':
if (orgoptions) {
orgoptions = strcat(orgoptions, ",");
orgoptions = strcat(orgoptions,optarg);
} else
orgoptions = strdup(optarg);
break;
/* case 'O':
if (test_opts)
test_opts = xstrconcat3(test_opts, ",", optarg);
else
test_opts = xstrdup(optarg);
break;*/
case 'r': /* mount readonly */
flags |= MS_RDONLY;;
break;
case 'U':
uuid = optarg;
break;
case 'v':
++verboseflag;
break;
/* case 'V':
printf ("mount: %s\n", version);
exit (0);*/
case 'w':
flags &= ~MS_RDONLY;;
break;
/* case 0:
break;
case 128:
mounttype = MS_BIND;
break;
case 129:
mounttype = MS_REPLACE;
break;
case 130:
mounttype = MS_AFTER;
break;
case 131:
mounttype = MS_BEFORE;
break;
case 132:
mounttype = MS_OVER;
break;
case 133:
mounttype = MS_MOVE;
break;
case 135:
mounttype = (MS_BIND | MS_REC);
break; */
case 136:
rsize = atoi(optarg) ;
break;
case 137:
wsize = atoi(optarg);
break;
case 138:
uid = atoi(optarg);
break;
case 139:
gid = atoi(optarg);
break;
case 140:
got_user = 1;
user_name = optarg;
break;
case 141:
domain_name = optarg;
break;
case 142:
got_password = 1;
mountpassword = optarg;
break;
case '?':
default:
mount_cifs_usage ();
}
}
/* canonicalize the path in argv[1]? */
if(stat (mountpoint, &statbuf)) {
printf("mount error: mount point %s does not exist\n",mountpoint);
return -1;
}
if (S_ISDIR(statbuf.st_mode) == 0) {
printf("mount error: mount point %s is not a directory\n",mountpoint);
return -1;
}
if(geteuid()) {
printf("mount error: permission denied, not superuser and cifs.mount not installed SUID\n");
return -1;
}
ipaddr = parse_server(share_name);
/* if(share_name == NULL)
return 1; */
if (parse_options(strdup(orgoptions)))
return 1;
if(got_user == 0)
user_name = getusername();
/* check username for user%password format */
if(got_password == 0) {
if (getenv("PASSWD")) {
mountpassword = malloc(33);
if(mountpassword) {
strncpy(mountpassword,getenv("PASSWD"),32);
got_password = 1;
}
/* } else if (getenv("PASSWD_FD") || getenv("PASSWD_FILE")) {
get_password_file();
got_password = 1;*/ /* BB add missing function */
} else {
mountpassword = getpass("Password: "); /* BB obsolete */
got_password = 1;
}
}
/* FIXME launch daemon (handles dfs name resolution and credential change)
remember to clear parms and overwrite password field before launching */
if(orgoptions) {
optlen = strlen(orgoptions);
} else
optlen = 0;
if(share_name)
optlen += strlen(share_name) + 4;
if(user_name)
optlen += strlen(user_name) + 6;
if(ipaddr)
optlen += strlen(ipaddr) + 4;
if(mountpassword)
optlen += strlen(mountpassword) + 6;
options = malloc(optlen + 10);
options[0] = 0;
strncat(options,"unc=",4);
strcat(options,share_name);
if(ipaddr) {
strncat(options,",ip=",4);
strcat(options,ipaddr);
}
if(user_name) {
strncat(options,",user=",6);
strcat(options,user_name);
}
if(mountpassword) {
strncat(options,",pass=",6);
strcat(options,mountpassword);
}
strncat(options,",ver=",5);
strcat(options,MOUNT_CIFS_VERSION);
if(orgoptions) {
strcat(options,",");
strcat(options,orgoptions);
}
/* printf("\noptions %s \n",options);*/
if(mount(share_name, mountpoint, "cifs", flags, options)) {
/* remember to kill daemon on error */
switch (errno) {
case 0:
printf("mount failed but no error number set\n");
return 0;
case ENODEV:
printf("mount error: cifs filesystem not supported by the system\n");
break;
default:
printf("mount error %d = %s",errno,strerror(errno));
}
printf("Refer to the mount.cifs(8) manual page (e.g.man mount.cifs)\n");
return -1;
} else {
pmntfile = setmntent(MOUNTED, "a+");
if(pmntfile) {
mountent.mnt_fsname = share_name;
mountent.mnt_dir = mountpoint;
mountent.mnt_type = "cifs";
mountent.mnt_opts = "";
mountent.mnt_freq = 0;
mountent.mnt_passno = 0;
rc = addmntent(pmntfile,&mountent);
endmntent(pmntfile);
} else {
printf("could not update mount table\n");
}
}
return 0;
}

306
source4/client/smbmnt.c Normal file
View File

@ -0,0 +1,306 @@
/*
* smbmnt.c
*
* Copyright (C) 1995-1998 by Paal-Kr. Engstad and Volker Lendecke
* extensively modified by Tridge
*
*/
#include "includes.h"
#include <mntent.h>
#include <sys/utsname.h>
#include <asm/types.h>
#include <asm/posix_types.h>
#include <linux/smb.h>
#include <linux/smb_mount.h>
#include <asm/unistd.h>
#ifndef MS_MGC_VAL
/* This may look strange but MS_MGC_VAL is what we are looking for and
is what we need from <linux/fs.h> under libc systems and is
provided in standard includes on glibc systems. So... We
switch on what we need... */
#include <linux/fs.h>
#endif
static uid_t mount_uid;
static gid_t mount_gid;
static int mount_ro;
static unsigned mount_fmask;
static unsigned mount_dmask;
static int user_mount;
static char *options;
static void
help(void)
{
printf("\n");
printf("Usage: smbmnt mount-point [options]\n");
printf("Version %s\n\n",VERSION);
printf("-s share share name on server\n"
"-r mount read-only\n"
"-u uid mount as uid\n"
"-g gid mount as gid\n"
"-f mask permission mask for files\n"
"-d mask permission mask for directories\n"
"-o options name=value, list of options\n"
"-h print this help text\n");
}
static int
parse_args(int argc, char *argv[], struct smb_mount_data *data, char **share)
{
int opt;
while ((opt = getopt (argc, argv, "s:u:g:rf:d:o:")) != EOF)
{
switch (opt)
{
case 's':
*share = optarg;
break;
case 'u':
if (!user_mount) {
mount_uid = strtol(optarg, NULL, 0);
}
break;
case 'g':
if (!user_mount) {
mount_gid = strtol(optarg, NULL, 0);
}
break;
case 'r':
mount_ro = 1;
break;
case 'f':
mount_fmask = strtol(optarg, NULL, 8);
break;
case 'd':
mount_dmask = strtol(optarg, NULL, 8);
break;
case 'o':
options = optarg;
break;
default:
return -1;
}
}
return 0;
}
static char *
fullpath(const char *p)
{
char path[MAXPATHLEN];
if (strlen(p) > MAXPATHLEN-1) {
return NULL;
}
if (realpath(p, path) == NULL) {
fprintf(stderr,"Failed to find real path for mount point\n");
exit(1);
}
return strdup(path);
}
/* Check whether user is allowed to mount on the specified mount point. If it's
OK then we change into that directory - this prevents race conditions */
static int mount_ok(char *mount_point)
{
struct stat st;
if (chdir(mount_point) != 0) {
return -1;
}
if (stat(".", &st) != 0) {
return -1;
}
if (!S_ISDIR(st.st_mode)) {
errno = ENOTDIR;
return -1;
}
if ((getuid() != 0) &&
((getuid() != st.st_uid) ||
((st.st_mode & S_IRWXU) != S_IRWXU))) {
errno = EPERM;
return -1;
}
return 0;
}
/* Tries to mount using the appropriate format. For 2.2 the struct,
for 2.4 the ascii version. */
static int
do_mount(char *share_name, unsigned int flags, struct smb_mount_data *data)
{
pstring opts;
struct utsname uts;
char *release, *major, *minor;
char *data1, *data2;
uname(&uts);
release = uts.release;
major = strtok(release, ".");
minor = strtok(NULL, ".");
if (major && minor && atoi(major) == 2 && atoi(minor) < 4) {
/* < 2.4, assume struct */
data1 = (char *) data;
data2 = opts;
} else {
/* >= 2.4, assume ascii but fall back on struct */
data1 = opts;
data2 = (char *) data;
}
slprintf(opts, sizeof(opts)-1,
"version=7,uid=%d,gid=%d,file_mode=0%o,dir_mode=0%o,%s",
data->uid, data->gid, data->file_mode, data->dir_mode,options);
if (mount(share_name, ".", "smbfs", flags, data1) == 0)
return 0;
return mount(share_name, ".", "smbfs", flags, data2);
}
int main(int argc, char *argv[])
{
char *mount_point, *share_name = NULL;
FILE *mtab;
int fd;
unsigned int flags;
struct smb_mount_data data;
struct mntent ment;
memset(&data, 0, sizeof(struct smb_mount_data));
if (argc < 2) {
help();
exit(1);
}
if (argv[1][0] == '-') {
help();
exit(1);
}
if (getuid() != 0) {
user_mount = 1;
}
if (geteuid() != 0) {
fprintf(stderr, "smbmnt must be installed suid root for direct user mounts (%d,%d)\n", getuid(), geteuid());
exit(1);
}
mount_uid = getuid();
mount_gid = getgid();
mount_fmask = umask(0);
umask(mount_fmask);
mount_fmask = ~mount_fmask;
mount_point = fullpath(argv[1]);
argv += 1;
argc -= 1;
if (mount_ok(mount_point) != 0) {
fprintf(stderr, "cannot mount on %s: %s\n",
mount_point, strerror(errno));
exit(1);
}
data.version = SMB_MOUNT_VERSION;
/* getuid() gives us the real uid, who may umount the fs */
data.mounted_uid = getuid();
if (parse_args(argc, argv, &data, &share_name) != 0) {
help();
return -1;
}
data.uid = mount_uid;
data.gid = mount_gid;
data.file_mode = (S_IRWXU|S_IRWXG|S_IRWXO) & mount_fmask;
data.dir_mode = (S_IRWXU|S_IRWXG|S_IRWXO) & mount_dmask;
if (mount_dmask == 0) {
data.dir_mode = data.file_mode;
if ((data.dir_mode & S_IRUSR) != 0)
data.dir_mode |= S_IXUSR;
if ((data.dir_mode & S_IRGRP) != 0)
data.dir_mode |= S_IXGRP;
if ((data.dir_mode & S_IROTH) != 0)
data.dir_mode |= S_IXOTH;
}
flags = MS_MGC_VAL;
if (mount_ro) flags |= MS_RDONLY;
if (do_mount(share_name, flags, &data) < 0) {
switch (errno) {
case ENODEV:
fprintf(stderr, "ERROR: smbfs filesystem not supported by the kernel\n");
break;
default:
perror("mount error");
}
fprintf(stderr, "Please refer to the smbmnt(8) manual page\n");
return -1;
}
ment.mnt_fsname = share_name ? share_name : "none";
ment.mnt_dir = mount_point;
ment.mnt_type = "smbfs";
ment.mnt_opts = "";
ment.mnt_freq = 0;
ment.mnt_passno= 0;
mount_point = ment.mnt_dir;
if (mount_point == NULL)
{
fprintf(stderr, "Mount point too long\n");
return -1;
}
if ((fd = open(MOUNTED"~", O_RDWR|O_CREAT|O_EXCL, 0600)) == -1)
{
fprintf(stderr, "Can't get "MOUNTED"~ lock file");
return 1;
}
close(fd);
if ((mtab = setmntent(MOUNTED, "a+")) == NULL)
{
fprintf(stderr, "Can't open " MOUNTED);
return 1;
}
if (addmntent(mtab, &ment) == 1)
{
fprintf(stderr, "Can't write mount entry");
return 1;
}
if (fchmod(fileno(mtab), 0644) == -1)
{
fprintf(stderr, "Can't set perms on "MOUNTED);
return 1;
}
endmntent(mtab);
if (unlink(MOUNTED"~") == -1)
{
fprintf(stderr, "Can't remove "MOUNTED"~");
return 1;
}
return 0;
}

930
source4/client/smbmount.c Normal file
View File

@ -0,0 +1,930 @@
/*
Unix SMB/CIFS implementation.
SMBFS mount program
Copyright (C) Andrew Tridgell 1999
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "includes.h"
#include <mntent.h>
#include <asm/types.h>
#include <linux/smb_fs.h>
extern BOOL in_client;
static pstring credentials;
static pstring my_netbios_name;
static pstring password;
static pstring username;
static pstring workgroup;
static pstring mpoint;
static pstring service;
static pstring options;
static struct in_addr dest_ip;
static BOOL have_ip;
static int smb_port = 0;
static BOOL got_user;
static BOOL got_pass;
static uid_t mount_uid;
static gid_t mount_gid;
static int mount_ro;
static unsigned mount_fmask;
static unsigned mount_dmask;
static BOOL use_kerberos;
/* TODO: Add code to detect smbfs version in kernel */
static BOOL status32_smbfs = False;
static void usage(void);
static void exit_parent(int sig)
{
/* parent simply exits when child says go... */
exit(0);
}
static void daemonize(void)
{
int j, status;
pid_t child_pid;
signal( SIGTERM, exit_parent );
if ((child_pid = sys_fork()) < 0) {
DEBUG(0,("could not fork\n"));
}
if (child_pid > 0) {
while( 1 ) {
j = waitpid( child_pid, &status, 0 );
if( j < 0 ) {
if( EINTR == errno ) {
continue;
}
status = errno;
}
break;
}
/* If we get here - the child exited with some error status */
if (WIFSIGNALED(status))
exit(128 + WTERMSIG(status));
else
exit(WEXITSTATUS(status));
}
signal( SIGTERM, SIG_DFL );
chdir("/");
}
static void close_our_files(int client_fd)
{
int i;
struct rlimit limits;
getrlimit(RLIMIT_NOFILE,&limits);
for (i = 0; i< limits.rlim_max; i++) {
if (i == client_fd)
continue;
close(i);
}
}
static void usr1_handler(int x)
{
return;
}
/*****************************************************
return a connection to a server
*******************************************************/
static struct cli_state *do_connection(char *the_service)
{
struct cli_state *c;
struct nmb_name called, calling;
char *server_n;
struct in_addr ip;
pstring server;
char *share;
if (the_service[0] != '\\' || the_service[1] != '\\') {
usage();
exit(1);
}
pstrcpy(server, the_service+2);
share = strchr_m(server,'\\');
if (!share) {
usage();
exit(1);
}
*share = 0;
share++;
server_n = server;
make_nmb_name(&calling, my_netbios_name, 0x0);
make_nmb_name(&called , server, 0x20);
again:
zero_ip(&ip);
if (have_ip) ip = dest_ip;
/* have to open a new connection */
if (!(c=cli_initialise(NULL)) || (cli_set_port(c, smb_port) != smb_port) ||
!cli_connect(c, server_n, &ip)) {
DEBUG(0,("%d: Connection to %s failed\n", sys_getpid(), server_n));
if (c) {
cli_shutdown(c);
}
return NULL;
}
/* SPNEGO doesn't work till we get NTSTATUS error support */
/* But it is REQUIRED for kerberos authentication */
if(!use_kerberos) c->use_spnego = False;
/* The kernel doesn't yet know how to sign it's packets */
c->sign_info.allow_smb_signing = False;
/* Use kerberos authentication if specified */
c->use_kerberos = use_kerberos;
if (!cli_session_request(c, &calling, &called)) {
char *p;
DEBUG(0,("%d: session request to %s failed (%s)\n",
sys_getpid(), called.name, cli_errstr(c)));
cli_shutdown(c);
if ((p=strchr_m(called.name, '.'))) {
*p = 0;
goto again;
}
if (strcmp(called.name, "*SMBSERVER")) {
make_nmb_name(&called , "*SMBSERVER", 0x20);
goto again;
}
return NULL;
}
DEBUG(4,("%d: session request ok\n", sys_getpid()));
if (!cli_negprot(c)) {
DEBUG(0,("%d: protocol negotiation failed\n", sys_getpid()));
cli_shutdown(c);
return NULL;
}
if (!got_pass) {
char *pass = getpass("Password: ");
if (pass) {
pstrcpy(password, pass);
}
}
/* This should be right for current smbfs. Future versions will support
large files as well as unicode and oplocks. */
if (status32_smbfs) {
c->capabilities &= ~(CAP_UNICODE | CAP_LARGE_FILES | CAP_NT_SMBS |
CAP_NT_FIND | CAP_LEVEL_II_OPLOCKS);
}
else {
c->capabilities &= ~(CAP_UNICODE | CAP_LARGE_FILES | CAP_NT_SMBS |
CAP_NT_FIND | CAP_STATUS32 |
CAP_LEVEL_II_OPLOCKS);
c->force_dos_errors = True;
}
if (!cli_session_setup(c, username,
password, strlen(password),
password, strlen(password),
workgroup)) {
/* if a password was not supplied then try again with a
null username */
if (password[0] || !username[0] ||
!cli_session_setup(c, "", "", 0, "", 0, workgroup)) {
DEBUG(0,("%d: session setup failed: %s\n",
sys_getpid(), cli_errstr(c)));
cli_shutdown(c);
return NULL;
}
DEBUG(0,("Anonymous login successful\n"));
}
DEBUG(4,("%d: session setup ok\n", sys_getpid()));
if (!cli_send_tconX(c, share, "?????",
password, strlen(password)+1)) {
DEBUG(0,("%d: tree connect failed: %s\n",
sys_getpid(), cli_errstr(c)));
cli_shutdown(c);
return NULL;
}
DEBUG(4,("%d: tconx ok\n", sys_getpid()));
got_pass = True;
return c;
}
/****************************************************************************
unmount smbfs (this is a bailout routine to clean up if a reconnect fails)
Code blatently stolen from smbumount.c
-mhw-
****************************************************************************/
static void smb_umount(char *mount_point)
{
int fd;
struct mntent *mnt;
FILE* mtab;
FILE* new_mtab;
/* Programmers Note:
This routine only gets called to the scene of a disaster
to shoot the survivors... A connection that was working
has now apparently failed. We have an active mount point
(presumably) that we need to dump. If we get errors along
the way - make some noise, but we are already turning out
the lights to exit anyways...
*/
if (umount(mount_point) != 0) {
DEBUG(0,("%d: Could not umount %s: %s\n",
sys_getpid(), mount_point, strerror(errno)));
return;
}
if ((fd = open(MOUNTED"~", O_RDWR|O_CREAT|O_EXCL, 0600)) == -1) {
DEBUG(0,("%d: Can't get "MOUNTED"~ lock file", sys_getpid()));
return;
}
close(fd);
if ((mtab = setmntent(MOUNTED, "r")) == NULL) {
DEBUG(0,("%d: Can't open " MOUNTED ": %s\n",
sys_getpid(), strerror(errno)));
return;
}
#define MOUNTED_TMP MOUNTED".tmp"
if ((new_mtab = setmntent(MOUNTED_TMP, "w")) == NULL) {
DEBUG(0,("%d: Can't open " MOUNTED_TMP ": %s\n",
sys_getpid(), strerror(errno)));
endmntent(mtab);
return;
}
while ((mnt = getmntent(mtab)) != NULL) {
if (strcmp(mnt->mnt_dir, mount_point) != 0) {
addmntent(new_mtab, mnt);
}
}
endmntent(mtab);
if (fchmod (fileno (new_mtab), S_IRUSR|S_IWUSR|S_IRGRP|S_IROTH) < 0) {
DEBUG(0,("%d: Error changing mode of %s: %s\n",
sys_getpid(), MOUNTED_TMP, strerror(errno)));
return;
}
endmntent(new_mtab);
if (rename(MOUNTED_TMP, MOUNTED) < 0) {
DEBUG(0,("%d: Cannot rename %s to %s: %s\n",
sys_getpid(), MOUNTED, MOUNTED_TMP, strerror(errno)));
return;
}
if (unlink(MOUNTED"~") == -1) {
DEBUG(0,("%d: Can't remove "MOUNTED"~", sys_getpid()));
return;
}
}
/*
* Call the smbfs ioctl to install a connection socket,
* then wait for a signal to reconnect. Note that we do
* not exit after open_sockets() or send_login() errors,
* as the smbfs mount would then have no way to recover.
*/
static void send_fs_socket(char *the_service, char *mount_point, struct cli_state *c)
{
int fd, closed = 0, res = 1;
pid_t parentpid = getppid();
struct smb_conn_opt conn_options;
memset(&conn_options, 0, sizeof(conn_options));
while (1) {
if ((fd = open(mount_point, O_RDONLY)) < 0) {
DEBUG(0,("mount.smbfs[%d]: can't open %s\n",
sys_getpid(), mount_point));
break;
}
conn_options.fd = c->fd;
conn_options.protocol = c->protocol;
conn_options.case_handling = SMB_CASE_DEFAULT;
conn_options.max_xmit = c->max_xmit;
conn_options.server_uid = c->vuid;
conn_options.tid = c->cnum;
conn_options.secmode = c->sec_mode;
conn_options.rawmode = 0;
conn_options.sesskey = c->sesskey;
conn_options.maxraw = 0;
conn_options.capabilities = c->capabilities;
conn_options.serverzone = c->serverzone/60;
res = ioctl(fd, SMB_IOC_NEWCONN, &conn_options);
if (res != 0) {
DEBUG(0,("mount.smbfs[%d]: ioctl failed, res=%d\n",
sys_getpid(), res));
close(fd);
break;
}
if (parentpid) {
/* Ok... We are going to kill the parent. Now
is the time to break the process group... */
setsid();
/* Send a signal to the parent to terminate */
kill(parentpid, SIGTERM);
parentpid = 0;
}
close(fd);
/* This looks wierd but we are only closing the userspace
side, the connection has already been passed to smbfs and
it has increased the usage count on the socket.
If we don't do this we will "leak" sockets and memory on
each reconnection we have to make. */
cli_shutdown(c);
c = NULL;
if (!closed) {
/* redirect stdout & stderr since we can't know that
the library functions we use are using DEBUG. */
if ( (fd = open("/dev/null", O_WRONLY)) < 0)
DEBUG(2,("mount.smbfs: can't open /dev/null\n"));
close_our_files(fd);
if (fd >= 0) {
dup2(fd, STDOUT_FILENO);
dup2(fd, STDERR_FILENO);
close(fd);
}
/* here we are no longer interactive */
set_remote_machine_name("smbmount"); /* sneaky ... */
setup_logging("mount.smbfs", False);
reopen_logs();
DEBUG(0, ("mount.smbfs: entering daemon mode for service %s, pid=%d\n", the_service, sys_getpid()));
closed = 1;
}
/* Wait for a signal from smbfs ... but don't continue
until we actually get a new connection. */
while (!c) {
CatchSignal(SIGUSR1, &usr1_handler);
pause();
DEBUG(2,("mount.smbfs[%d]: got signal, getting new socket\n", sys_getpid()));
c = do_connection(the_service);
}
}
smb_umount(mount_point);
DEBUG(2,("mount.smbfs[%d]: exit\n", sys_getpid()));
exit(1);
}
/**
* Mount a smbfs
**/
static void init_mount(void)
{
char mount_point[MAXPATHLEN+1];
pstring tmp;
pstring svc2;
struct cli_state *c;
char *args[20];
int i, status;
if (realpath(mpoint, mount_point) == NULL) {
fprintf(stderr, "Could not resolve mount point %s\n", mpoint);
return;
}
c = do_connection(service);
if (!c) {
fprintf(stderr,"SMB connection failed\n");
exit(1);
}
/*
Set up to return as a daemon child and wait in the parent
until the child say it's ready...
*/
daemonize();
pstrcpy(svc2, service);
string_replace(svc2, '\\','/');
string_replace(svc2, ' ','_');
memset(args, 0, sizeof(args[0])*20);
i=0;
args[i++] = "smbmnt";
args[i++] = mount_point;
args[i++] = "-s";
args[i++] = svc2;
if (mount_ro) {
args[i++] = "-r";
}
if (mount_uid) {
slprintf(tmp, sizeof(tmp)-1, "%d", mount_uid);
args[i++] = "-u";
args[i++] = smb_xstrdup(tmp);
}
if (mount_gid) {
slprintf(tmp, sizeof(tmp)-1, "%d", mount_gid);
args[i++] = "-g";
args[i++] = smb_xstrdup(tmp);
}
if (mount_fmask) {
slprintf(tmp, sizeof(tmp)-1, "0%o", mount_fmask);
args[i++] = "-f";
args[i++] = smb_xstrdup(tmp);
}
if (mount_dmask) {
slprintf(tmp, sizeof(tmp)-1, "0%o", mount_dmask);
args[i++] = "-d";
args[i++] = smb_xstrdup(tmp);
}
if (options) {
args[i++] = "-o";
args[i++] = options;
}
if (sys_fork() == 0) {
char *smbmnt_path;
asprintf(&smbmnt_path, "%s/smbmnt", dyn_BINDIR);
if (file_exist(smbmnt_path, NULL)) {
execv(smbmnt_path, args);
fprintf(stderr,
"smbfs/init_mount: execv of %s failed. Error was %s.",
smbmnt_path, strerror(errno));
} else {
execvp("smbmnt", args);
fprintf(stderr,
"smbfs/init_mount: execv of %s failed. Error was %s.",
"smbmnt", strerror(errno));
}
free(smbmnt_path);
exit(1);
}
if (waitpid(-1, &status, 0) == -1) {
fprintf(stderr,"waitpid failed: Error was %s", strerror(errno) );
/* FIXME: do some proper error handling */
exit(1);
}
if (WIFEXITED(status) && WEXITSTATUS(status) != 0) {
fprintf(stderr,"smbmnt failed: %d\n", WEXITSTATUS(status));
/* FIXME: do some proper error handling */
exit(1);
} else if (WIFSIGNALED(status)) {
fprintf(stderr, "smbmnt killed by signal %d\n", WTERMSIG(status));
exit(1);
}
/* Ok... This is the rubicon for that mount point... At any point
after this, if the connections fail and can not be reconstructed
for any reason, we will have to unmount the mount point. There
is no exit from the next call...
*/
send_fs_socket(service, mount_point, c);
}
/****************************************************************************
get a password from a a file or file descriptor
exit on failure (from smbclient, move to libsmb or shared .c file?)
****************************************************************************/
static void get_password_file(void)
{
int fd = -1;
char *p;
BOOL close_it = False;
pstring spec;
char pass[128];
if ((p = getenv("PASSWD_FD")) != NULL) {
pstrcpy(spec, "descriptor ");
pstrcat(spec, p);
sscanf(p, "%d", &fd);
close_it = False;
} else if ((p = getenv("PASSWD_FILE")) != NULL) {
fd = sys_open(p, O_RDONLY, 0);
pstrcpy(spec, p);
if (fd < 0) {
fprintf(stderr, "Error opening PASSWD_FILE %s: %s\n",
spec, strerror(errno));
exit(1);
}
close_it = True;
}
for(p = pass, *p = '\0'; /* ensure that pass is null-terminated */
p && p - pass < sizeof(pass);) {
switch (read(fd, p, 1)) {
case 1:
if (*p != '\n' && *p != '\0') {
*++p = '\0'; /* advance p, and null-terminate pass */
break;
}
case 0:
if (p - pass) {
*p = '\0'; /* null-terminate it, just in case... */
p = NULL; /* then force the loop condition to become false */
break;
} else {
fprintf(stderr, "Error reading password from file %s: %s\n",
spec, "empty password\n");
exit(1);
}
default:
fprintf(stderr, "Error reading password from file %s: %s\n",
spec, strerror(errno));
exit(1);
}
}
pstrcpy(password, pass);
if (close_it)
close(fd);
}
/****************************************************************************
get username and password from a credentials file
exit on failure (from smbclient, move to libsmb or shared .c file?)
****************************************************************************/
static void read_credentials_file(char *filename)
{
FILE *auth;
fstring buf;
uint16 len = 0;
char *ptr, *val, *param;
if ((auth=sys_fopen(filename, "r")) == NULL)
{
/* fail if we can't open the credentials file */
DEBUG(0,("ERROR: Unable to open credentials file!\n"));
exit (-1);
}
while (!feof(auth))
{
/* get a line from the file */
if (!fgets (buf, sizeof(buf), auth))
continue;
len = strlen(buf);
if ((len) && (buf[len-1]=='\n'))
{
buf[len-1] = '\0';
len--;
}
if (len == 0)
continue;
/* break up the line into parameter & value.
will need to eat a little whitespace possibly */
param = buf;
if (!(ptr = strchr (buf, '=')))
continue;
val = ptr+1;
*ptr = '\0';
/* eat leading white space */
while ((*val!='\0') && ((*val==' ') || (*val=='\t')))
val++;
if (strwicmp("password", param) == 0)
{
pstrcpy(password, val);
got_pass = True;
}
else if (strwicmp("username", param) == 0) {
pstrcpy(username, val);
}
memset(buf, 0, sizeof(buf));
}
fclose(auth);
}
/****************************************************************************
usage on the program
****************************************************************************/
static void usage(void)
{
printf("Usage: mount.smbfs service mountpoint [-o options,...]\n");
printf("Version %s\n\n",VERSION);
printf(
"Options:\n\
username=<arg> SMB username\n\
password=<arg> SMB password\n\
credentials=<filename> file with username/password\n\
krb use kerberos (active directory)\n\
netbiosname=<arg> source NetBIOS name\n\
uid=<arg> mount uid or username\n\
gid=<arg> mount gid or groupname\n\
port=<arg> remote SMB port number\n\
fmask=<arg> file umask\n\
dmask=<arg> directory umask\n\
debug=<arg> debug level\n\
ip=<arg> destination host or IP address\n\
workgroup=<arg> workgroup on destination\n\
sockopt=<arg> TCP socket options\n\
scope=<arg> NetBIOS scope\n\
iocharset=<arg> Linux charset (iso8859-1, utf8)\n\
codepage=<arg> server codepage (cp850)\n\
ttl=<arg> dircache time to live\n\
guest don't prompt for a password\n\
ro mount read-only\n\
rw mount read-write\n\
\n\
This command is designed to be run from within /bin/mount by giving\n\
the option '-t smbfs'. For example:\n\
mount -t smbfs -o username=tridge,password=foobar //fjall/test /data/test\n\
");
}
/****************************************************************************
Argument parsing for mount.smbfs interface
mount will call us like this:
mount.smbfs device mountpoint -o <options>
<options> is never empty, containing at least rw or ro
****************************************************************************/
static void parse_mount_smb(int argc, char **argv)
{
int opt;
char *opts;
char *opteq;
extern char *optarg;
int val;
char *p;
/* FIXME: This function can silently fail if the arguments are
* not in the expected order.
> The arguments syntax of smbmount 2.2.3a (smbfs of Debian stable)
> requires that one gives "-o" before further options like username=...
> . Without -o, the username=.. setting is *silently* ignored. I've
> spent about an hour trying to find out why I couldn't log in now..
*/
if (argc < 2 || argv[1][0] == '-') {
usage();
exit(1);
}
pstrcpy(service, argv[1]);
pstrcpy(mpoint, argv[2]);
/* Convert any '/' characters in the service name to
'\' characters */
string_replace(service, '/','\\');
argc -= 2;
argv += 2;
opt = getopt(argc, argv, "o:");
if(opt != 'o') {
return;
}
options[0] = 0;
p = options;
/*
* option parsing from nfsmount.c (util-linux-2.9u)
*/
for (opts = strtok(optarg, ","); opts; opts = strtok(NULL, ",")) {
DEBUG(3, ("opts: %s\n", opts));
if ((opteq = strchr_m(opts, '='))) {
val = atoi(opteq + 1);
*opteq = '\0';
if (!strcmp(opts, "username") ||
!strcmp(opts, "logon")) {
char *lp;
got_user = True;
pstrcpy(username,opteq+1);
if ((lp=strchr_m(username,'%'))) {
*lp = 0;
pstrcpy(password,lp+1);
got_pass = True;
memset(strchr_m(opteq+1,'%')+1,'X',strlen(password));
}
if ((lp=strchr_m(username,'/'))) {
*lp = 0;
pstrcpy(workgroup,lp+1);
}
} else if(!strcmp(opts, "passwd") ||
!strcmp(opts, "password")) {
pstrcpy(password,opteq+1);
got_pass = True;
memset(opteq+1,'X',strlen(password));
} else if(!strcmp(opts, "credentials")) {
pstrcpy(credentials,opteq+1);
} else if(!strcmp(opts, "netbiosname")) {
pstrcpy(my_netbios_name,opteq+1);
} else if(!strcmp(opts, "uid")) {
mount_uid = nametouid(opteq+1);
} else if(!strcmp(opts, "gid")) {
mount_gid = nametogid(opteq+1);
} else if(!strcmp(opts, "port")) {
smb_port = val;
} else if(!strcmp(opts, "fmask")) {
mount_fmask = strtol(opteq+1, NULL, 8);
} else if(!strcmp(opts, "dmask")) {
mount_dmask = strtol(opteq+1, NULL, 8);
} else if(!strcmp(opts, "debug")) {
DEBUGLEVEL = val;
} else if(!strcmp(opts, "ip")) {
dest_ip = *interpret_addr2(opteq+1);
if (is_zero_ip(dest_ip)) {
fprintf(stderr,"Can't resolve address %s\n", opteq+1);
exit(1);
}
have_ip = True;
} else if(!strcmp(opts, "workgroup")) {
pstrcpy(workgroup,opteq+1);
} else if(!strcmp(opts, "sockopt")) {
lp_set_cmdline("socket options", opteq+1);
} else if(!strcmp(opts, "scope")) {
lp_set_cmdline("netbios scope", opteq+1);
} else {
slprintf(p, sizeof(pstring) - (p - options) - 1, "%s=%s,", opts, opteq+1);
p += strlen(p);
}
} else {
val = 1;
if(!strcmp(opts, "nocaps")) {
fprintf(stderr, "Unhandled option: %s\n", opteq+1);
exit(1);
} else if(!strcmp(opts, "guest")) {
*password = '\0';
got_pass = True;
} else if(!strcmp(opts, "krb")) {
#ifdef HAVE_KRB5
use_kerberos = True;
if(!status32_smbfs)
fprintf(stderr, "Warning: kerberos support will only work for samba servers\n");
#else
fprintf(stderr,"No kerberos support compiled in\n");
exit(1);
#endif
} else if(!strcmp(opts, "rw")) {
mount_ro = 0;
} else if(!strcmp(opts, "ro")) {
mount_ro = 1;
} else {
strncpy(p, opts, sizeof(pstring) - (p - options) - 1);
p += strlen(opts);
*p++ = ',';
*p = 0;
}
}
}
if (!*service) {
usage();
exit(1);
}
if (p != options) {
*(p-1) = 0; /* remove trailing , */
DEBUG(3,("passthrough options '%s'\n", options));
}
}
/****************************************************************************
main program
****************************************************************************/
int main(int argc,char *argv[])
{
extern char *optarg;
extern int optind;
char *p;
DEBUGLEVEL = 1;
/* here we are interactive, even if run from autofs */
setup_logging("mount.smbfs",True);
#if 0 /* JRA - Urban says not needed ? */
/* CLI_FORCE_ASCII=false makes smbmount negotiate unicode. The default
is to not announce any unicode capabilities as current smbfs does
not support it. */
p = getenv("CLI_FORCE_ASCII");
if (p && !strcmp(p, "false"))
unsetenv("CLI_FORCE_ASCII");
else
setenv("CLI_FORCE_ASCII", "true", 1);
#endif
in_client = True; /* Make sure that we tell lp_load we are */
if (getenv("USER")) {
pstrcpy(username,getenv("USER"));
if ((p=strchr_m(username,'%'))) {
*p = 0;
pstrcpy(password,p+1);
got_pass = True;
memset(strchr_m(getenv("USER"),'%')+1,'X',strlen(password));
}
strupper(username);
}
if (getenv("PASSWD")) {
pstrcpy(password,getenv("PASSWD"));
got_pass = True;
}
if (getenv("PASSWD_FD") || getenv("PASSWD_FILE")) {
get_password_file();
got_pass = True;
}
if (*username == 0 && getenv("LOGNAME")) {
pstrcpy(username,getenv("LOGNAME"));
}
if (!lp_load(dyn_CONFIGFILE,True,False,False)) {
fprintf(stderr, "Can't load %s - run testparm to debug it\n",
dyn_CONFIGFILE);
}
parse_mount_smb(argc, argv);
if (use_kerberos && !got_user) {
got_pass = True;
}
if (*credentials != 0) {
read_credentials_file(credentials);
}
DEBUG(3,("mount.smbfs started (version %s)\n", VERSION));
if (*workgroup == 0) {
pstrcpy(workgroup,lp_workgroup());
}
load_interfaces();
if (!*my_netbios_name) {
pstrcpy(my_netbios_name, myhostname());
}
strupper(my_netbios_name);
init_mount();
return 0;
}

362
source4/client/smbspool.c Normal file
View File

@ -0,0 +1,362 @@
/*
Unix SMB/CIFS implementation.
SMB backend for the Common UNIX Printing System ("CUPS")
Copyright 1999 by Easy Software Products
Copyright Andrew Tridgell 1994-1998
Copyright Andrew Bartlett 2002
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "includes.h"
/*
* Globals...
*/
extern BOOL in_client; /* Boolean for client library */
/*
* Local functions...
*/
static void list_devices(void);
static struct cli_state *smb_connect(const char *, const char *, const char *, const char *, const char *);
static int smb_print(struct cli_state *, char *, FILE *);
/*
* 'main()' - Main entry for SMB backend.
*/
int /* O - Exit status */
main(int argc, /* I - Number of command-line arguments */
char *argv[]) /* I - Command-line arguments */
{
int i; /* Looping var */
int copies; /* Number of copies */
char uri[1024], /* URI */
*sep, /* Pointer to separator */
*password; /* Password */
const char *username, /* Username */
*server, /* Server name */
*printer; /* Printer name */
const char *workgroup; /* Workgroup */
FILE *fp; /* File to print */
int status=0; /* Status of LPD job */
struct cli_state *cli; /* SMB interface */
/* we expect the URI in argv[0]. Detect the case where it is in argv[1] and cope */
if (argc > 2 && strncmp(argv[0],"smb://", 6) && !strncmp(argv[1],"smb://", 6)) {
argv++;
argc--;
}
if (argc == 1)
{
/*
* NEW! In CUPS 1.1 the backends are run with no arguments to list the
* available devices. These can be devices served by this backend
* or any other backends (i.e. you can have an SNMP backend that
* is only used to enumerate the available network printers... :)
*/
list_devices();
return (0);
}
if (argc < 6 || argc > 7)
{
fprintf(stderr, "Usage: %s [DEVICE_URI] job-id user title copies options [file]\n",
argv[0]);
fputs(" The DEVICE_URI environment variable can also contain the\n", stderr);
fputs(" destination printer:\n", stderr);
fputs("\n", stderr);
fputs(" smb://[username:password@][workgroup/]server/printer\n", stderr);
return (1);
}
/*
* If we have 7 arguments, print the file named on the command-line.
* Otherwise, print data from stdin...
*/
if (argc == 6)
{
/*
* Print from Copy stdin to a temporary file...
*/
fp = stdin;
copies = 1;
}
else if ((fp = fopen(argv[6], "rb")) == NULL)
{
perror("ERROR: Unable to open print file");
return (1);
}
else
copies = atoi(argv[4]);
/*
* Find the URI...
*/
if (strncmp(argv[0], "smb://", 6) == 0)
strncpy(uri, argv[0], sizeof(uri) - 1);
else if (getenv("DEVICE_URI") != NULL)
strncpy(uri, getenv("DEVICE_URI"), sizeof(uri) - 1);
else
{
fputs("ERROR: No device URI found in argv[0] or DEVICE_URI environment variable!\n", stderr);
return (1);
}
uri[sizeof(uri) - 1] = '\0';
/*
* Extract the destination from the URI...
*/
if ((sep = strrchr_m(uri, '@')) != NULL)
{
username = uri + 6;
*sep++ = '\0';
server = sep;
/*
* Extract password as needed...
*/
if ((password = strchr_m(username, ':')) != NULL)
*password++ = '\0';
else
password = "";
}
else
{
username = "";
password = "";
server = uri + 6;
}
if ((sep = strchr_m(server, '/')) == NULL)
{
fputs("ERROR: Bad URI - need printer name!\n", stderr);
return (1);
}
*sep++ = '\0';
printer = sep;
if ((sep = strchr_m(printer, '/')) != NULL)
{
/*
* Convert to smb://[username:password@]workgroup/server/printer...
*/
*sep++ = '\0';
workgroup = server;
server = printer;
printer = sep;
}
else
workgroup = NULL;
/*
* Setup the SAMBA server state...
*/
setup_logging("smbspool", True);
in_client = True; /* Make sure that we tell lp_load we are */
if (!lp_load(dyn_CONFIGFILE, True, False, False))
{
fprintf(stderr, "ERROR: Can't load %s - run testparm to debug it\n", dyn_CONFIGFILE);
return (1);
}
if (workgroup == NULL)
workgroup = lp_workgroup();
load_interfaces();
do
{
if ((cli = smb_connect(workgroup, server, printer, username, password)) == NULL)
{
if (getenv("CLASS") == NULL)
{
fprintf(stderr, "ERROR: Unable to connect to SAMBA host, will retry in 60 seconds...");
sleep (60);
}
else
{
fprintf(stderr, "ERROR: Unable to connect to SAMBA host, trying next printer...");
return (1);
}
}
}
while (cli == NULL);
/*
* Now that we are connected to the server, ignore SIGTERM so that we
* can finish out any page data the driver sends (e.g. to eject the
* current page... Only ignore SIGTERM if we are printing data from
* stdin (otherwise you can't cancel raw jobs...)
*/
if (argc < 7)
CatchSignal(SIGTERM, SIG_IGN);
/*
* Queue the job...
*/
for (i = 0; i < copies; i ++)
if ((status = smb_print(cli, argv[3] /* title */, fp)) != 0)
break;
cli_shutdown(cli);
/*
* Return the queue status...
*/
return (status);
}
/*
* 'list_devices()' - List the available printers seen on the network...
*/
static void
list_devices(void)
{
/*
* Eventually, search the local workgroup for available hosts and printers.
*/
puts("network smb \"Unknown\" \"Windows Printer via SAMBA\"");
}
/*
* 'smb_connect()' - Return a connection to a server.
*/
static struct cli_state * /* O - SMB connection */
smb_connect(const char *workgroup, /* I - Workgroup */
const char *server, /* I - Server */
const char *share, /* I - Printer */
const char *username, /* I - Username */
const char *password) /* I - Password */
{
struct cli_state *c; /* New connection */
char *myname; /* Client name */
NTSTATUS nt_status;
/*
* Get the names and addresses of the client and server...
*/
myname = get_myname();
nt_status = cli_full_connection(&c, myname, server, NULL, 0, share, "?????",
username, workgroup, password, 0, NULL);
free(myname);
if (!NT_STATUS_IS_OK(nt_status)) {
fprintf(stderr, "ERROR: Connection failed with error %s\n", nt_errstr(nt_status));
return NULL;
}
/*
* Return the new connection...
*/
return (c);
}
/*
* 'smb_print()' - Queue a job for printing using the SMB protocol.
*/
static int /* O - 0 = success, non-0 = failure */
smb_print(struct cli_state *cli, /* I - SMB connection */
char *title, /* I - Title/job name */
FILE *fp) /* I - File to print */
{
int fnum; /* File number */
int nbytes, /* Number of bytes read */
tbytes; /* Total bytes read */
char buffer[8192], /* Buffer for copy */
*ptr; /* Pointer into tile */
/*
* Sanitize the title...
*/
for (ptr = title; *ptr; ptr ++)
if (!isalnum((int)*ptr) && !isspace((int)*ptr))
*ptr = '_';
/*
* Open the printer device...
*/
if ((fnum = cli_open(cli, title, O_RDWR | O_CREAT | O_TRUNC, DENY_NONE)) == -1)
{
fprintf(stderr, "ERROR: %s opening remote file %s\n",
cli_errstr(cli), title);
return (1);
}
/*
* Copy the file to the printer...
*/
if (fp != stdin)
rewind(fp);
tbytes = 0;
while ((nbytes = fread(buffer, 1, sizeof(buffer), fp)) > 0)
{
if (cli_write(cli, fnum, 0, buffer, tbytes, nbytes) != nbytes)
{
fprintf(stderr, "ERROR: Error writing file: %s\n", cli_errstr(cli));
break;
}
tbytes += nbytes;
}
if (!cli_close(cli, fnum))
{
fprintf(stderr, "ERROR: %s closing remote file %s\n",
cli_errstr(cli), title);
return (1);
}
else
return (0);
}

186
source4/client/smbumount.c Normal file
View File

@ -0,0 +1,186 @@
/*
* smbumount.c
*
* Copyright (C) 1995-1998 by Volker Lendecke
*
*/
#include "includes.h"
#include <mntent.h>
#include <asm/types.h>
#include <asm/posix_types.h>
#include <linux/smb.h>
#include <linux/smb_mount.h>
#include <linux/smb_fs.h>
/* This is a (hopefully) temporary hack due to the fact that
sizeof( uid_t ) != sizeof( __kernel_uid_t ) under glibc.
This may change in the future and smb.h may get fixed in the
future. In the mean time, it's ugly hack time - get over it.
*/
#undef SMB_IOC_GETMOUNTUID
#define SMB_IOC_GETMOUNTUID _IOR('u', 1, __kernel_uid_t)
#ifndef O_NOFOLLOW
#define O_NOFOLLOW 0400000
#endif
static void
usage(void)
{
printf("usage: smbumount mountpoint\n");
}
static int
umount_ok(const char *mount_point)
{
/* we set O_NOFOLLOW to prevent users playing games with symlinks to
umount filesystems they don't own */
int fid = open(mount_point, O_RDONLY|O_NOFOLLOW, 0);
__kernel_uid_t mount_uid;
if (fid == -1) {
fprintf(stderr, "Could not open %s: %s\n",
mount_point, strerror(errno));
return -1;
}
if (ioctl(fid, SMB_IOC_GETMOUNTUID, &mount_uid) != 0) {
fprintf(stderr, "%s probably not smb-filesystem\n",
mount_point);
return -1;
}
if ((getuid() != 0)
&& (mount_uid != getuid())) {
fprintf(stderr, "You are not allowed to umount %s\n",
mount_point);
return -1;
}
close(fid);
return 0;
}
/* Make a canonical pathname from PATH. Returns a freshly malloced string.
It is up the *caller* to ensure that the PATH is sensible. i.e.
canonicalize ("/dev/fd0/.") returns "/dev/fd0" even though ``/dev/fd0/.''
is not a legal pathname for ``/dev/fd0'' Anything we cannot parse
we return unmodified. */
static char *
canonicalize (char *path)
{
char *canonical = malloc (PATH_MAX + 1);
if (!canonical) {
fprintf(stderr, "Error! Not enough memory!\n");
return NULL;
}
if (strlen(path) > PATH_MAX) {
fprintf(stderr, "Mount point string too long\n");
return NULL;
}
if (path == NULL)
return NULL;
if (realpath (path, canonical))
return canonical;
strncpy (canonical, path, PATH_MAX);
canonical[PATH_MAX] = '\0';
return canonical;
}
int
main(int argc, char *argv[])
{
int fd;
char* mount_point;
struct mntent *mnt;
FILE* mtab;
FILE* new_mtab;
if (argc != 2) {
usage();
exit(1);
}
if (geteuid() != 0) {
fprintf(stderr, "smbumount must be installed suid root\n");
exit(1);
}
mount_point = canonicalize(argv[1]);
if (mount_point == NULL)
{
exit(1);
}
if (umount_ok(mount_point) != 0) {
exit(1);
}
if (umount(mount_point) != 0) {
fprintf(stderr, "Could not umount %s: %s\n",
mount_point, strerror(errno));
exit(1);
}
if ((fd = open(MOUNTED"~", O_RDWR|O_CREAT|O_EXCL, 0600)) == -1)
{
fprintf(stderr, "Can't get "MOUNTED"~ lock file");
return 1;
}
close(fd);
if ((mtab = setmntent(MOUNTED, "r")) == NULL) {
fprintf(stderr, "Can't open " MOUNTED ": %s\n",
strerror(errno));
return 1;
}
#define MOUNTED_TMP MOUNTED".tmp"
if ((new_mtab = setmntent(MOUNTED_TMP, "w")) == NULL) {
fprintf(stderr, "Can't open " MOUNTED_TMP ": %s\n",
strerror(errno));
endmntent(mtab);
return 1;
}
while ((mnt = getmntent(mtab)) != NULL) {
if (strcmp(mnt->mnt_dir, mount_point) != 0) {
addmntent(new_mtab, mnt);
}
}
endmntent(mtab);
if (fchmod (fileno (new_mtab), S_IRUSR|S_IWUSR|S_IRGRP|S_IROTH) < 0) {
fprintf(stderr, "Error changing mode of %s: %s\n",
MOUNTED_TMP, strerror(errno));
exit(1);
}
endmntent(new_mtab);
if (rename(MOUNTED_TMP, MOUNTED) < 0) {
fprintf(stderr, "Cannot rename %s to %s: %s\n",
MOUNTED, MOUNTED_TMP, strerror(errno));
exit(1);
}
if (unlink(MOUNTED"~") == -1)
{
fprintf(stderr, "Can't remove "MOUNTED"~");
return 1;
}
return 0;
}

811
source4/client/tree.c Normal file
View File

@ -0,0 +1,811 @@
/*
Unix SMB/CIFS implementation.
SMB client GTK+ tree-based application
Copyright (C) Andrew Tridgell 1998
Copyright (C) Richard Sharpe 2001
Copyright (C) John Terpstra 2001
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* example-gtk+ application, ripped off from the gtk+ tree.c sample */
#include <stdio.h>
#include <errno.h>
#include <gtk/gtk.h>
#include "libsmbclient.h"
static GtkWidget *clist;
struct tree_data {
guint32 type; /* Type of tree item, an SMBC_TYPE */
char name[256]; /* May need to change this later */
};
void error_message(gchar *message) {
GtkWidget *dialog, *label, *okay_button;
/* Create the widgets */
dialog = gtk_dialog_new();
gtk_window_set_modal(GTK_WINDOW(dialog), True);
label = gtk_label_new (message);
okay_button = gtk_button_new_with_label("Okay");
/* Ensure that the dialog box is destroyed when the user clicks ok. */
gtk_signal_connect_object (GTK_OBJECT (okay_button), "clicked",
GTK_SIGNAL_FUNC (gtk_widget_destroy), dialog);
gtk_container_add (GTK_CONTAINER (GTK_DIALOG(dialog)->action_area),
okay_button);
/* Add the label, and show everything we've added to the dialog. */
gtk_container_add (GTK_CONTAINER (GTK_DIALOG(dialog)->vbox),
label);
gtk_widget_show_all (dialog);
}
/*
* We are given a widget, and we want to retrieve its URL so we
* can do a directory listing.
*
* We walk back up the tree, picking up pieces until we hit a server or
* workgroup type and return a path from there
*/
static char path_string[1024];
char *get_path(GtkWidget *item)
{
GtkWidget *p = item;
struct tree_data *pd;
char *comps[1024]; /* We keep pointers to the components here */
int i = 0, j, level,type;
/* Walk back up the tree, getting the private data */
level = GTK_TREE(item->parent)->level;
/* Pick up this item's component info */
pd = (struct tree_data *)gtk_object_get_user_data(GTK_OBJECT(item));
comps[i++] = pd->name;
type = pd->type;
while (level > 0 && type != SMBC_SERVER && type != SMBC_WORKGROUP) {
/* Find the parent and extract the data etc ... */
p = GTK_WIDGET(p->parent);
p = GTK_WIDGET(GTK_TREE(p)->tree_owner);
pd = (struct tree_data *)gtk_object_get_user_data(GTK_OBJECT(p));
level = GTK_TREE(item->parent)->level;
comps[i++] = pd->name;
type = pd->type;
}
/*
* Got a list of comps now, should check that we did not hit a workgroup
* when we got other things as well ... Later
*
* Now, build the path
*/
snprintf(path_string, sizeof(path_string), "smb:/");
for (j = i - 1; j >= 0; j--) {
strncat(path_string, "/", sizeof(path_string) - strlen(path_string));
strncat(path_string, comps[j], sizeof(path_string) - strlen(path_string));
}
fprintf(stdout, "Path string = %s\n", path_string);
return path_string;
}
struct tree_data *make_tree_data(guint32 type, const char *name)
{
struct tree_data *p = (struct tree_data *)malloc(sizeof(struct tree_data));
if (p) {
p->type = type;
strncpy(p->name, name, sizeof(p->name));
}
return p;
}
/* Note that this is called every time the user clicks on an item,
whether it is already selected or not. */
static void cb_select_child (GtkWidget *root_tree, GtkWidget *child,
GtkWidget *subtree)
{
gint dh, err, dirlen;
char dirbuf[512];
struct smbc_dirent *dirp;
struct stat st1;
char path[1024], path1[1024];
g_print ("select_child called for root tree %p, subtree %p, child %p\n",
root_tree, subtree, child);
/* Now, figure out what it is, and display it in the clist ... */
gtk_clist_clear(GTK_CLIST(clist)); /* Clear the CLIST */
/* Now, get the private data for the subtree */
strncpy(path, get_path(child), 1024);
if ((dh = smbc_opendir(path)) < 0) { /* Handle error */
g_print("cb_select_child: Could not open dir %s, %s\n", path,
strerror(errno));
gtk_main_quit();
return;
}
while ((err = smbc_getdents(dh, (struct smbc_dirent *)dirbuf,
sizeof(dirbuf))) != 0) {
if (err < 0) {
g_print("cb_select_child: Could not read dir %s, %s\n", path,
strerror(errno));
gtk_main_quit();
return;
}
dirp = (struct smbc_dirent *)dirbuf;
while (err > 0) {
gchar col1[128], col2[128], col3[128], col4[128];
gchar *rowdata[4] = {col1, col2, col3, col4};
dirlen = dirp->dirlen;
/* Format each of the items ... */
strncpy(col1, dirp->name, 128);
col2[0] = col3[0] = col4[0] = (char)0;
switch (dirp->smbc_type) {
case SMBC_WORKGROUP:
break;
case SMBC_SERVER:
strncpy(col2, (dirp->comment?dirp->comment:""), 128);
break;
case SMBC_FILE_SHARE:
strncpy(col2, (dirp->comment?dirp->comment:""), 128);
break;
case SMBC_PRINTER_SHARE:
strncpy(col2, (dirp->comment?dirp->comment:""), 128);
break;
case SMBC_COMMS_SHARE:
break;
case SMBC_IPC_SHARE:
break;
case SMBC_DIR:
case SMBC_FILE:
/* Get stats on the file/dir and see what we have */
if ((strcmp(dirp->name, ".") != 0) &&
(strcmp(dirp->name, "..") != 0)) {
strncpy(path1, path, sizeof(path1));
strncat(path1, "/", sizeof(path) - strlen(path));
strncat(path1, dirp->name, sizeof(path) - strlen(path));
if (smbc_stat(path1, &st1) < 0) {
if (errno != EBUSY) {
g_print("cb_select_child: Could not stat file %s, %s\n", path1,
strerror(errno));
gtk_main_quit();
return;
}
else {
strncpy(col2, "Device or resource busy", sizeof(col2));
}
}
else {
/* Now format each of the relevant things ... */
snprintf(col2, sizeof(col2), "%c%c%c%c%c%c%c%c%c(%0X)",
(st1.st_mode&S_IRUSR?'r':'-'),
(st1.st_mode&S_IWUSR?'w':'-'),
(st1.st_mode&S_IXUSR?'x':'-'),
(st1.st_mode&S_IRGRP?'r':'-'),
(st1.st_mode&S_IWGRP?'w':'-'),
(st1.st_mode&S_IXGRP?'x':'-'),
(st1.st_mode&S_IROTH?'r':'-'),
(st1.st_mode&S_IWOTH?'w':'-'),
(st1.st_mode&S_IXOTH?'x':'-'),
st1.st_mode);
snprintf(col3, sizeof(col3), "%u", st1.st_size);
snprintf(col4, sizeof(col4), "%s", ctime(&st1.st_mtime));
}
}
break;
default:
break;
}
gtk_clist_append(GTK_CLIST(clist), rowdata);
(char *)dirp += dirlen;
err -= dirlen;
}
}
}
/* Note that this is never called */
static void cb_unselect_child( GtkWidget *root_tree,
GtkWidget *child,
GtkWidget *subtree )
{
g_print ("unselect_child called for root tree %p, subtree %p, child %p\n",
root_tree, subtree, child);
}
/* for all the GtkItem:: and GtkTreeItem:: signals */
static void cb_itemsignal( GtkWidget *item,
gchar *signame )
{
GtkWidget *real_tree, *aitem, *subtree;
gchar *name;
GtkLabel *label;
gint dh, err, dirlen, level;
char dirbuf[512];
struct smbc_dirent *dirp;
label = GTK_LABEL (GTK_BIN (item)->child);
/* Get the text of the label */
gtk_label_get (label, &name);
level = GTK_TREE(item->parent)->level;
/* Get the level of the tree which the item is in */
g_print ("%s called for item %s->%p, level %d\n", signame, name,
item, GTK_TREE (item->parent)->level);
real_tree = GTK_TREE_ITEM_SUBTREE(item); /* Get the subtree */
if (strncmp(signame, "expand", 6) == 0) { /* Expand called */
char server[128];
if ((dh = smbc_opendir(get_path(item))) < 0) { /* Handle error */
gchar errmsg[256];
g_print("cb_itemsignal: Could not open dir %s, %s\n", get_path(item),
strerror(errno));
slprintf(errmsg, sizeof(errmsg), "cb_itemsignal: Could not open dir %s, %s\n", get_path(item), strerror(errno));
error_message(errmsg);
/* gtk_main_quit();*/
return;
}
while ((err = smbc_getdents(dh, (struct smbc_dirent *)dirbuf,
sizeof(dirbuf))) != 0) {
if (err < 0) { /* An error, report it */
gchar errmsg[256];
g_print("cb_itemsignal: Could not read dir smbc://, %s\n",
strerror(errno));
slprintf(errmsg, sizeof(errmsg), "cb_itemsignal: Could not read dir smbc://, %s\n", strerror(errno));
error_message(errmsg);
/* gtk_main_quit();*/
return;
}
dirp = (struct smbc_dirent *)dirbuf;
while (err > 0) {
struct tree_data *my_data;
dirlen = dirp->dirlen;
my_data = make_tree_data(dirp->smbc_type, dirp->name);
if (!my_data) {
g_print("Could not allocate space for tree_data: %s\n",
dirp->name);
gtk_main_quit();
return;
}
aitem = gtk_tree_item_new_with_label(dirp->name);
/* Connect all GtkItem:: and GtkTreeItem:: signals */
gtk_signal_connect (GTK_OBJECT(aitem), "select",
GTK_SIGNAL_FUNC(cb_itemsignal), "select");
gtk_signal_connect (GTK_OBJECT(aitem), "deselect",
GTK_SIGNAL_FUNC(cb_itemsignal), "deselect");
gtk_signal_connect (GTK_OBJECT(aitem), "toggle",
GTK_SIGNAL_FUNC(cb_itemsignal), "toggle");
gtk_signal_connect (GTK_OBJECT(aitem), "expand",
GTK_SIGNAL_FUNC(cb_itemsignal), "expand");
gtk_signal_connect (GTK_OBJECT(aitem), "collapse",
GTK_SIGNAL_FUNC(cb_itemsignal), "collapse");
/* Add it to the parent tree */
gtk_tree_append (GTK_TREE(real_tree), aitem);
gtk_widget_show (aitem);
gtk_object_set_user_data(GTK_OBJECT(aitem), (gpointer)my_data);
fprintf(stdout, "Added: %s, len: %u\n", dirp->name, dirlen);
if (dirp->smbc_type != SMBC_FILE &&
dirp->smbc_type != SMBC_IPC_SHARE &&
(strcmp(dirp->name, ".") != 0) &&
(strcmp(dirp->name, "..") !=0)){
subtree = gtk_tree_new();
gtk_tree_item_set_subtree(GTK_TREE_ITEM(aitem), subtree);
gtk_signal_connect(GTK_OBJECT(subtree), "select_child",
GTK_SIGNAL_FUNC(cb_select_child), real_tree);
gtk_signal_connect(GTK_OBJECT(subtree), "unselect_child",
GTK_SIGNAL_FUNC(cb_unselect_child), real_tree);
}
(char *)dirp += dirlen;
err -= dirlen;
}
}
smbc_closedir(dh);
}
else if (strncmp(signame, "collapse", 8) == 0) {
GtkWidget *subtree = gtk_tree_new();
gtk_tree_remove_items(GTK_TREE(real_tree), GTK_TREE(real_tree)->children);
gtk_tree_item_set_subtree(GTK_TREE_ITEM(item), subtree);
gtk_signal_connect (GTK_OBJECT(subtree), "select_child",
GTK_SIGNAL_FUNC(cb_select_child), real_tree);
gtk_signal_connect (GTK_OBJECT(subtree), "unselect_child",
GTK_SIGNAL_FUNC(cb_unselect_child), real_tree);
}
}
static void cb_selection_changed( GtkWidget *tree )
{
GList *i;
g_print ("selection_change called for tree %p\n", tree);
g_print ("selected objects are:\n");
i = GTK_TREE_SELECTION(tree);
while (i){
gchar *name;
GtkLabel *label;
GtkWidget *item;
/* Get a GtkWidget pointer from the list node */
item = GTK_WIDGET (i->data);
label = GTK_LABEL (GTK_BIN (item)->child);
gtk_label_get (label, &name);
g_print ("\t%s on level %d\n", name, GTK_TREE
(item->parent)->level);
i = i->next;
}
}
/*
* Expand or collapse the whole network ...
*/
static void cb_wholenet(GtkWidget *item, gchar *signame)
{
GtkWidget *real_tree, *aitem, *subtree;
gchar *name;
GtkLabel *label;
gint dh, err, dirlen;
char dirbuf[512];
struct smbc_dirent *dirp;
label = GTK_LABEL (GTK_BIN (item)->child);
gtk_label_get (label, &name);
g_print ("%s called for item %s->%p, level %d\n", signame, name,
item, GTK_TREE (item->parent)->level);
real_tree = GTK_TREE_ITEM_SUBTREE(item); /* Get the subtree */
if (strncmp(signame, "expand", 6) == 0) { /* Expand called */
if ((dh = smbc_opendir("smb://")) < 0) { /* Handle error */
g_print("cb_wholenet: Could not open dir smbc://, %s\n",
strerror(errno));
gtk_main_quit();
return;
}
while ((err = smbc_getdents(dh, (struct smbc_dirent *)dirbuf,
sizeof(dirbuf))) != 0) {
if (err < 0) { /* An error, report it */
g_print("cb_wholenet: Could not read dir smbc://, %s\n",
strerror(errno));
gtk_main_quit();
return;
}
dirp = (struct smbc_dirent *)dirbuf;
while (err > 0) {
struct tree_data *my_data;
dirlen = dirp->dirlen;
my_data = make_tree_data(dirp->smbc_type, dirp->name);
aitem = gtk_tree_item_new_with_label(dirp->name);
/* Connect all GtkItem:: and GtkTreeItem:: signals */
gtk_signal_connect (GTK_OBJECT(aitem), "select",
GTK_SIGNAL_FUNC(cb_itemsignal), "select");
gtk_signal_connect (GTK_OBJECT(aitem), "deselect",
GTK_SIGNAL_FUNC(cb_itemsignal), "deselect");
gtk_signal_connect (GTK_OBJECT(aitem), "toggle",
GTK_SIGNAL_FUNC(cb_itemsignal), "toggle");
gtk_signal_connect (GTK_OBJECT(aitem), "expand",
GTK_SIGNAL_FUNC(cb_itemsignal), "expand");
gtk_signal_connect (GTK_OBJECT(aitem), "collapse",
GTK_SIGNAL_FUNC(cb_itemsignal), "collapse");
gtk_tree_append (GTK_TREE(real_tree), aitem);
/* Show it - this can be done at any time */
gtk_widget_show (aitem);
gtk_object_set_user_data(GTK_OBJECT(aitem), (gpointer)my_data);
fprintf(stdout, "Added: %s, len: %u\n", dirp->name, dirlen);
subtree = gtk_tree_new();
gtk_tree_item_set_subtree(GTK_TREE_ITEM(aitem), subtree);
gtk_signal_connect(GTK_OBJECT(subtree), "select_child",
GTK_SIGNAL_FUNC(cb_select_child), real_tree);
gtk_signal_connect(GTK_OBJECT(subtree), "unselect_child",
GTK_SIGNAL_FUNC(cb_unselect_child), real_tree);
(char *)dirp += dirlen;
err -= dirlen;
}
}
smbc_closedir(dh);
}
else { /* Must be collapse ... FIXME ... */
GtkWidget *subtree = gtk_tree_new();
gtk_tree_remove_items(GTK_TREE(real_tree), GTK_TREE(real_tree)->children);
gtk_tree_item_set_subtree(GTK_TREE_ITEM(item), subtree);
gtk_signal_connect (GTK_OBJECT(subtree), "select_child",
GTK_SIGNAL_FUNC(cb_select_child), real_tree);
gtk_signal_connect (GTK_OBJECT(subtree), "unselect_child",
GTK_SIGNAL_FUNC(cb_unselect_child), real_tree);
}
}
/* Should put up a dialog box to ask the user for username and password */
static void
auth_fn(const char *server, const char *share,
char *workgroup, int wgmaxlen, char *username, int unmaxlen,
char *password, int pwmaxlen)
{
strncpy(username, "test", unmaxlen);
strncpy(password, "test", pwmaxlen);
}
static char *col_titles[] = {
"Name", "Attributes", "Size", "Modification Date",
};
int main( int argc,
char *argv[] )
{
GtkWidget *window, *scrolled_win, *scrolled_win2, *tree;
GtkWidget *subtree, *item, *main_hbox, *r_pane, *l_pane;
gint err, dh;
gint i;
char dirbuf[512];
struct smbc_dirent *dirp;
gtk_init (&argc, &argv);
/* Init the smbclient library */
err = smbc_init(auth_fn, 10);
/* Print an error response ... */
if (err < 0) {
fprintf(stderr, "smbc_init returned %s (%i)\nDo you have a ~/.smb/smb.conf file?\n", strerror(errno), errno);
exit(1);
}
/* a generic toplevel window */
window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
gtk_widget_set_name(window, "main browser window");
gtk_signal_connect (GTK_OBJECT(window), "delete_event",
GTK_SIGNAL_FUNC (gtk_main_quit), NULL);
gtk_window_set_title(GTK_WINDOW(window), "The Linux Windows Network Browser");
gtk_widget_set_usize(GTK_WIDGET(window), 750, -1);
gtk_container_set_border_width (GTK_CONTAINER(window), 5);
gtk_widget_show (window);
/* A container for the two panes ... */
main_hbox = gtk_hbox_new(FALSE, 1);
gtk_container_border_width(GTK_CONTAINER(main_hbox), 1);
gtk_container_add(GTK_CONTAINER(window), main_hbox);
gtk_widget_show(main_hbox);
l_pane = gtk_hpaned_new();
gtk_paned_gutter_size(GTK_PANED(l_pane), (GTK_PANED(l_pane))->handle_size);
r_pane = gtk_hpaned_new();
gtk_paned_gutter_size(GTK_PANED(r_pane), (GTK_PANED(r_pane))->handle_size);
gtk_container_add(GTK_CONTAINER(main_hbox), l_pane);
gtk_widget_show(l_pane);
/* A generic scrolled window */
scrolled_win = gtk_scrolled_window_new (NULL, NULL);
gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scrolled_win),
GTK_POLICY_AUTOMATIC,
GTK_POLICY_AUTOMATIC);
gtk_widget_set_usize (scrolled_win, 150, 200);
gtk_container_add (GTK_CONTAINER(l_pane), scrolled_win);
gtk_widget_show (scrolled_win);
/* Another generic scrolled window */
scrolled_win2 = gtk_scrolled_window_new (NULL, NULL);
gtk_scrolled_window_set_policy (GTK_SCROLLED_WINDOW (scrolled_win2),
GTK_POLICY_AUTOMATIC,
GTK_POLICY_AUTOMATIC);
gtk_widget_set_usize (scrolled_win2, 150, 200);
gtk_paned_add2 (GTK_PANED(l_pane), scrolled_win2);
gtk_widget_show (scrolled_win2);
/* Create the root tree */
tree = gtk_tree_new();
g_print ("root tree is %p\n", tree);
/* connect all GtkTree:: signals */
gtk_signal_connect (GTK_OBJECT(tree), "select_child",
GTK_SIGNAL_FUNC(cb_select_child), tree);
gtk_signal_connect (GTK_OBJECT(tree), "unselect_child",
GTK_SIGNAL_FUNC(cb_unselect_child), tree);
gtk_signal_connect (GTK_OBJECT(tree), "selection_changed",
GTK_SIGNAL_FUNC(cb_selection_changed), tree);
/* Add it to the scrolled window */
gtk_scrolled_window_add_with_viewport (GTK_SCROLLED_WINDOW(scrolled_win),
tree);
/* Set the selection mode */
gtk_tree_set_selection_mode (GTK_TREE(tree),
GTK_SELECTION_MULTIPLE);
/* Show it */
gtk_widget_show (tree);
/* Now, create a clist and attach it to the second pane */
clist = gtk_clist_new_with_titles(4, col_titles);
gtk_container_add (GTK_CONTAINER(scrolled_win2), clist);
gtk_widget_show(clist);
/* Now, build the top level display ... */
if ((dh = smbc_opendir("smb:///")) < 0) {
fprintf(stderr, "Could not list default workgroup: smb:///: %s\n",
strerror(errno));
exit(1);
}
/* Create a tree item for Whole Network */
item = gtk_tree_item_new_with_label ("Whole Network");
/* Connect all GtkItem:: and GtkTreeItem:: signals */
gtk_signal_connect (GTK_OBJECT(item), "select",
GTK_SIGNAL_FUNC(cb_itemsignal), "select");
gtk_signal_connect (GTK_OBJECT(item), "deselect",
GTK_SIGNAL_FUNC(cb_itemsignal), "deselect");
gtk_signal_connect (GTK_OBJECT(item), "toggle",
GTK_SIGNAL_FUNC(cb_itemsignal), "toggle");
gtk_signal_connect (GTK_OBJECT(item), "expand",
GTK_SIGNAL_FUNC(cb_wholenet), "expand");
gtk_signal_connect (GTK_OBJECT(item), "collapse",
GTK_SIGNAL_FUNC(cb_wholenet), "collapse");
/* Add it to the parent tree */
gtk_tree_append (GTK_TREE(tree), item);
/* Show it - this can be done at any time */
gtk_widget_show (item);
subtree = gtk_tree_new(); /* A subtree for Whole Network */
gtk_tree_item_set_subtree(GTK_TREE_ITEM(item), subtree);
gtk_signal_connect (GTK_OBJECT(subtree), "select_child",
GTK_SIGNAL_FUNC(cb_select_child), tree);
gtk_signal_connect (GTK_OBJECT(subtree), "unselect_child",
GTK_SIGNAL_FUNC(cb_unselect_child), tree);
/* Now, get the items in smb:/// and add them to the tree */
dirp = (struct smbc_dirent *)dirbuf;
while ((err = smbc_getdents(dh, (struct smbc_dirent *)dirbuf,
sizeof(dirbuf))) != 0) {
if (err < 0) { /* Handle the error */
fprintf(stderr, "Could not read directory for smbc:///: %s\n",
strerror(errno));
exit(1);
}
fprintf(stdout, "Dir len: %u\n", err);
while (err > 0) { /* Extract each entry and make a sub-tree */
struct tree_data *my_data;
int dirlen = dirp->dirlen;
my_data = make_tree_data(dirp->smbc_type, dirp->name);
item = gtk_tree_item_new_with_label(dirp->name);
/* Connect all GtkItem:: and GtkTreeItem:: signals */
gtk_signal_connect (GTK_OBJECT(item), "select",
GTK_SIGNAL_FUNC(cb_itemsignal), "select");
gtk_signal_connect (GTK_OBJECT(item), "deselect",
GTK_SIGNAL_FUNC(cb_itemsignal), "deselect");
gtk_signal_connect (GTK_OBJECT(item), "toggle",
GTK_SIGNAL_FUNC(cb_itemsignal), "toggle");
gtk_signal_connect (GTK_OBJECT(item), "expand",
GTK_SIGNAL_FUNC(cb_itemsignal), "expand");
gtk_signal_connect (GTK_OBJECT(item), "collapse",
GTK_SIGNAL_FUNC(cb_itemsignal), "collapse");
/* Add it to the parent tree */
gtk_tree_append (GTK_TREE(tree), item);
/* Show it - this can be done at any time */
gtk_widget_show (item);
gtk_object_set_user_data(GTK_OBJECT(item), (gpointer)my_data);
fprintf(stdout, "Added: %s, len: %u\n", dirp->name, dirlen);
subtree = gtk_tree_new();
gtk_tree_item_set_subtree(GTK_TREE_ITEM(item), subtree);
gtk_signal_connect (GTK_OBJECT(subtree), "select_child",
GTK_SIGNAL_FUNC(cb_select_child), tree);
gtk_signal_connect (GTK_OBJECT(subtree), "unselect_child",
GTK_SIGNAL_FUNC(cb_unselect_child), tree);
(char *)dirp += dirlen;
err -= dirlen;
}
}
smbc_closedir(dh); /* FIXME, check for error :-) */
/* Show the window and loop endlessly */
gtk_main();
return 0;
}
/* example-end */

View File

BIN
source4/codepages/valid.dat Normal file

Binary file not shown.

1473
source4/config.sub vendored Executable file

File diff suppressed because it is too large Load Diff

2
source4/configure.developer Executable file
View File

@ -0,0 +1,2 @@
#!/bin/sh
`dirname $0`/configure --enable-developer $*

3455
source4/configure.in Normal file

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,3 @@
#!/bin/sh
CFLAGS="-Wall -Wshadow -Wstrict-prototypes -Wpointer-arith -Wcast-qual -Wcast-align -DDEBUG_PASSWORD"; export CFLAGS
./configure $*

3
source4/configure.tridge.opt Executable file
View File

@ -0,0 +1,3 @@
#!/bin/sh
export CFLAGS="-O2 -Wall"
`dirname $0`/configure $* --prefix=/home/tridge/samba/samba4/prefix

72
source4/dynconfig.c Normal file
View File

@ -0,0 +1,72 @@
/*
Unix SMB/CIFS implementation.
Copyright (C) 2001 by Martin Pool <mbp@samba.org>
Copyright (C) 2003 by Anthony Liguori <aliguor@us.ibm.com>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "includes.h"
/**
* @file dynconfig.c
*
* @brief Global configurations, initialized to configured defaults.
*
* This file should be the only file that depends on path
* configuration (--prefix, etc), so that if ./configure is re-run,
* all programs will be appropriately updated. Everything else in
* Samba should import extern variables from here, rather than relying
* on preprocessor macros.
*
* Eventually some of these may become even more variable, so that
* they can for example consistently be set across the whole of Samba
* by command-line parameters, config file entries, or environment
* variables.
*
* @todo Perhaps eventually these should be merged into the parameter
* table? There's kind of a chicken-and-egg situation there...
**/
char const *dyn_SBINDIR = SBINDIR,
*dyn_BINDIR = BINDIR,
*dyn_SWATDIR = SWATDIR;
pstring dyn_CONFIGFILE = CONFIGFILE; /**< Location of smb.conf file. **/
/** Log file directory. **/
const char *dyn_LOGFILEBASE = LOGFILEBASE;
/** Statically configured LanMan hosts. **/
pstring dyn_LMHOSTSFILE = LMHOSTSFILE;
/**
* @brief Samba library directory.
*
* @sa lib_path() to get the path to a file inside the LIBDIR.
**/
pstring dyn_LIBDIR = LIBDIR;
const fstring dyn_SHLIBEXT = SHLIBEXT;
/**
* @brief Directory holding lock files.
*
* Not writable, but used to set a default in the parameter table.
**/
const pstring dyn_LOCKDIR = LOCKDIR;
const pstring dyn_PIDDIR = PIDDIR;
const pstring dyn_SMB_PASSWD_FILE = SMB_PASSWD_FILE;
const pstring dyn_PRIVATE_DIR = PRIVATE_DIR;

1340
source4/groupdb/mapping.c Normal file

File diff suppressed because it is too large Load Diff

4
source4/ignore.txt Normal file
View File

@ -0,0 +1,4 @@
all_info.out.fname
compression_info.out.*_shift
internal_information.out.*
stream_info.out.streams[i].size

View File

@ -0,0 +1,8 @@
build_env.h
config.h
config.h.in
includes.h.gch
proto.h
stamp-h
tdbsam2_parse_info.h
wrepld_proto.h

View File

@ -0,0 +1,246 @@
/*
Unix SMB/CIFS implementation.
SMB parameters and setup
Copyright (C) Andrew Tridgell 1992-1998
Copyright (C) John H Terpstra 1996-1998
Copyright (C) Luke Kenneth Casson Leighton 1996-1998
Copyright (C) Paul Ashton 1998
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _MAC_EXTENSIONS_H
#define _MAC_EXTENSIONS_H
/* Folder that holds the stream info */
#define STREAM_FOLDER ".streams"
#define STREAM_FOLDER_SLASH ".streams/"
/* Common Streams Names*/
#define DefaultStreamTestLen 6
#define DefaultStreamTest ":$DATA"
#define AFPDATA_STREAM "::$DATA"
#define AFPINFO_STREAM ":AFP_AfpInfo:$DATA"
#define AFPRESOURCE_STREAM ":AFP_Resource:$DATA"
#define AFPCOMMENTS_STREAM ":Comments:$DATA"
#define AFPDESKTOP_STREAM ":AFP_DeskTop:$DATA"
#define AFPIDINDEX_STREAM ":AFP_IdIndex:$DATA"
/*
** NT's AFP_AfpInfo stream structure
*/
#define APF_INFO_SIZE 0x3c
#define AFP_Signature 0x41465000
#define AFP_Version 0x00000100
#define AFP_BackupTime 0x00000080
#define AFP_FinderSize 32
/*
** Orginal AFP_AfpInfo stream used by NT
** We needed a way to store the create date so SAMBA
** AFP_AfpInfo adds for bytes to this structrure
** and call's it _SambaAfpInfo
*/
typedef struct _AfpInfo
{
uint32 afpi_Signature; /* Must be *(PDWORD)"AFP" */
uint32 afpi_Version; /* Must be 0x00010000 */
uint32 afpi_Reserved1;
uint32 afpi_BackupTime; /* Backup time for the file/dir */
unsigned char afpi_FinderInfo[AFP_FinderSize]; /* Finder Info (32 bytes) */
unsigned char afpi_ProDosInfo[6]; /* ProDos Info (6 bytes) # */
unsigned char afpi_Reserved2[6];
} AfpInfo;
typedef struct _SambaAfpInfo
{
AfpInfo afp;
unsigned long createtime;
} SambaAfpInfo;
/*
** On SAMBA this structrue is followed by 4 bytes that store the create
** date of the file or folder asociated with it.
*/
/*
** These extentions are only supported with the NT LM 0.12 Dialect. These extentions
** will be process on a share by share bases.
*/
/*
** Trans2_Query_FS_Information Call is used by the MacCIFS extentions for three reasons.
** First to see if the remote server share supports the basic Macintosh CIFS extentions.
** Second to return some basic need information about the share to the Macintosh.
** Third to see if this share support any other Macintosh extentions.
**
** We will be using infromation levels that are betwwen 0x300 and 0x399 for all Macintosh
** extentions calls. The first of these will be the SMB_MAC_QUERY_FS_INFO level which
** will allow the server to return the MacQueryFSInfo structure. All fields are Little
** Endian unless other wise specified.
*/
#define SMB_MAC_QUERY_FS_INFO 0x301
/*
** The server will return folder access control in the Trans2_Find_First2
** and Trans2_Find_Next2 message described later in this document.
*/
#define SUPPORT_MAC_ACCESS_CNTRL 0x0010
/*
** The server supports setting/getting comments using the mechanism in this
** document instead of using the NTFS format described in the Introduction.
*/
#define SUPPORT_MAC_GETSETCOMMENTS 0x0020
/*
** The Server supports setting and getting Macintosh desktop database information
** using the mechanism in this document.
*/
#define SUPPORT_MAC_DESKTOPDB_CALLS 0x0040
/*
** The server will return a unique id for files and directories in the
** Trans2_Find_First2 and Trans2_Find_Next2 message described later in this document.
*/
#define SUPPORT_MAC_UNIQUE_IDS 0x0080
/*
** The server will return this flag telling the client that the server does
** not support streams or the Macintosh extensions. The rest of this message
** will be ignored by the client.
*/
#define NO_STREAMS_OR_MAC_SUPPORT 0x0100
/*
** We will be adding a new info level to the Trans2_Find_First2 and Trans2_Find_Next2.
** This info level will be SMB_MAC_FIND_BOTH_HFS_INFO and will support the server
** return additional information need by the Macintosh. All fields are Little
** Endian unless other wise specified.
*/
#define SMB_MAC_FIND_BOTH_HFS_INFO 0x302
enum {
ownerRead = 0x0400,
ownerWrite = 0x0200,
ownerSearch = 0x0100,
groupRead = 0x0040,
groupWrite = 0x0020,
groupSearch = 0x0010,
otherRead = 0x0004,
otherWrite = 0x0002,
otherSearch = 0x0001,
Owner = 0x0800
};
/*
** We will be adding a new info level to the Trans2_Set_Path_Information.
** This info level will be SMB_MAC_SET_FINDER_INFO and will support the client
** setting information on the server need by the Macintosh. All fields are Little
** Endian unless other wise specified.
*/
#define SMB_MAC_SET_FINDER_INFO 0x303
enum {
SetCreateDate = 0x01, /* If this is set then set the create date of the file/folder */
SetModDate = 0x02, /* If this is set then set the modify date of the file/folder */
SetFLAttrib = 0x04, /* If this is set then set the Macintosh lock bit of the file/folder */
FndrInfo1 = 0x08, /* If this is set then set the first 16 bytes of finder info */
FndrInfo2 = 0x10, /* If this is set then set the second 16 bytes of finder info */
SetHidden = 0x20 /* We are either setting or unsetting the hidden bit */
};
/*
** We will be adding some new info level to the Trans2_Set_Path_Information and Trans2_Query_Path_Information.
** These info levels will allow the client to add, get, and remove desktop inforamtion from the
** server. How the server stores this information is up to them.
*/
/*
** We need to be able to store an application name and its creator in a database. We send a
** Trans2_Set_Path_Information call with the full path of the application in the path field.
** We will send an info level that represents adding an application name and creator to the database.
** We will pass the File Creator in the data message.
**
** The server should just respond with no error or an error.
*/
#define SMB_MAC_DT_ADD_APPL 0x304
/*
** We need to be able to remove an application name and its creator from a database. We send a
** Trans2_Set_Path_Information call with the full path of the application in the path field.
** We will send an info level that represents removing an application name and creator from the database.
** We will pass the File Creator in the data message.
**
** The server should just respond with no error or an error.
*/
#define SMB_MAC_DT_REMOVE_APPL 0x305
/*
** We need to be able to get an application name and its creator from a database. We send a
** Trans2_Query_Path_Information call in which the name field is just ignore.
** We will send an info level that represents getting an application name with a structure that
** contains the File Creator and index. Were index has the following meaning.
** Index = 0; Get the application path from the database with the most current date.
** Index > 0; Use the index to find the application path from the database.
** e.g. index of 5 means get the fifth entry of this application name in the database.
** if not entry return an error.
**
** The server returns with a structure that contains the full path to the appication and
** its creator's date.
*/
#define SMB_MAC_DT_GET_APPL 0x306
/*
** We need to be able to get an icon from a database. We send a Trans2_Query_Path_Information call in
** which the path name is ignore. We will send an info level that represents getting an icon with a structure
** that contains the Requested size of the icon, the Icon type, File Creator, and File Type.
**
** The server returns with a structure that contains the actual size of the icon
** (must be less than requested length) and the icon bit map.
*/
#define SMB_MAC_DT_GET_ICON 0x307
/*
** We need to be able to get an icon from a database. We send a Trans2_Query_Path_Information call in
** which the path name is ignore. We will send an info level that represents getting an icon with a structure
** that contains the index and File Creator. The index allows the client to make repeated calls to the server
** gathering all icon stored by this file creator.
**
**
** The server returns with a structure that contains the actual size of the icon
** (must be less than requested length) and the icon bit map, File Type, and Icon Type.
*/
#define SMB_MAC_DT_GET_ICON_INFO 0x308
/*
** We need to be able to add an icon to a database. We send a Trans2_Set_Path_Information call in
** which the path name is ignore. We will send an info level that represents setting an icon with a structure
** that contains the icon data, icon size, icon type, the file type, and file creator.
**
**
** The server returns only that the call was succesfull or not.
*/
#define SMB_MAC_DT_ADD_ICON 0x309
#endif /* _MAC_EXTENSIONS_H */
/* _MAC_EXTENSIONS_H */

215
source4/include/ads.h Normal file
View File

@ -0,0 +1,215 @@
/*
header for ads (active directory) library routines
basically this is a wrapper around ldap
*/
typedef struct {
void *ld; /* the active ldap structure */
struct in_addr ldap_ip; /* the ip of the active connection, if any */
time_t last_attempt; /* last attempt to reconnect */
int ldap_port;
/* info needed to find the server */
struct {
char *realm;
char *workgroup;
char *ldap_server;
char *ldap_uri;
int foreign; /* set to 1 if connecting to a foreign realm */
} server;
/* info needed to authenticate */
struct {
char *realm;
char *password;
char *user_name;
char *kdc_server;
unsigned flags;
int time_offset;
} auth;
/* info derived from the servers config */
struct {
char *realm;
char *bind_path;
char *ldap_server_name;
time_t current_time;
} config;
} ADS_STRUCT;
/* there are 4 possible types of errors the ads subsystem can produce */
enum ads_error_type {ADS_ERROR_KRB5, ADS_ERROR_GSS,
ADS_ERROR_LDAP, ADS_ERROR_SYSTEM, ADS_ERROR_NT};
typedef struct {
enum ads_error_type error_type;
union err_state{
int rc;
NTSTATUS nt_status;
} err;
/* For error_type = ADS_ERROR_GSS minor_status describe GSS API error */
/* Where rc represents major_status of GSS API error */
int minor_status;
} ADS_STATUS;
#ifdef HAVE_ADS
typedef LDAPMod **ADS_MODLIST;
#else
typedef void **ADS_MODLIST;
#endif
/* macros to simplify error returning */
#define ADS_ERROR(rc) ADS_ERROR_LDAP(rc)
#define ADS_ERROR_LDAP(rc) ads_build_error(ADS_ERROR_LDAP, rc, 0)
#define ADS_ERROR_SYSTEM(rc) ads_build_error(ADS_ERROR_SYSTEM, rc?rc:EINVAL, 0)
#define ADS_ERROR_KRB5(rc) ads_build_error(ADS_ERROR_KRB5, rc, 0)
#define ADS_ERROR_GSS(rc, minor) ads_build_error(ADS_ERROR_GSS, rc, minor)
#define ADS_ERROR_NT(rc) ads_build_nt_error(ADS_ERROR_NT,rc)
#define ADS_ERR_OK(status) ((status.error_type == ADS_ERROR_NT) ? NT_STATUS_IS_OK(status.err.nt_status):(status.err.rc == 0))
#define ADS_SUCCESS ADS_ERROR(0)
/* time between reconnect attempts */
#define ADS_RECONNECT_TIME 5
/* timeout on searches */
#define ADS_SEARCH_TIMEOUT 10
/* ldap control oids */
#define ADS_PAGE_CTL_OID "1.2.840.113556.1.4.319"
#define ADS_NO_REFERRALS_OID "1.2.840.113556.1.4.1339"
#define ADS_SERVER_SORT_OID "1.2.840.113556.1.4.473"
#define ADS_PERMIT_MODIFY_OID "1.2.840.113556.1.4.1413"
/* UserFlags for userAccountControl */
#define UF_SCRIPT 0x00000001
#define UF_ACCOUNTDISABLE 0x00000002
#define UF_UNUSED_1 0x00000004
#define UF_HOMEDIR_REQUIRED 0x00000008
#define UF_LOCKOUT 0x00000010
#define UF_PASSWD_NOTREQD 0x00000020
#define UF_PASSWD_CANT_CHANGE 0x00000040
#define UF_ENCRYPTED_TEXT_PASSWORD_ALLOWED 0x00000080
#define UF_TEMP_DUPLICATE_ACCOUNT 0x00000100
#define UF_NORMAL_ACCOUNT 0x00000200
#define UF_UNUSED_2 0x00000400
#define UF_INTERDOMAIN_TRUST_ACCOUNT 0x00000800
#define UF_WORKSTATION_TRUST_ACCOUNT 0x00001000
#define UF_SERVER_TRUST_ACCOUNT 0x00002000
#define UF_UNUSED_3 0x00004000
#define UF_UNUSED_4 0x00008000
#define UF_DONT_EXPIRE_PASSWD 0x00010000
#define UF_MNS_LOGON_ACCOUNT 0x00020000
#define UF_SMARTCARD_REQUIRED 0x00040000
#define UF_TRUSTED_FOR_DELEGATION 0x00080000
#define UF_NOT_DELEGATED 0x00100000
#define UF_USE_DES_KEY_ONLY 0x00200000
#define UF_DONT_REQUIRE_PREAUTH 0x00400000
#define UF_UNUSED_5 0x00800000
#define UF_UNUSED_6 0x01000000
#define UF_UNUSED_7 0x02000000
#define UF_UNUSED_8 0x04000000
#define UF_UNUSED_9 0x08000000
#define UF_UNUSED_10 0x10000000
#define UF_UNUSED_11 0x20000000
#define UF_UNUSED_12 0x40000000
#define UF_UNUSED_13 0x80000000
#define UF_MACHINE_ACCOUNT_MASK (\
UF_INTERDOMAIN_TRUST_ACCOUNT |\
UF_WORKSTATION_TRUST_ACCOUNT |\
UF_SERVER_TRUST_ACCOUNT \
)
#define UF_ACCOUNT_TYPE_MASK (\
UF_TEMP_DUPLICATE_ACCOUNT |\
UF_NORMAL_ACCOUNT |\
UF_INTERDOMAIN_TRUST_ACCOUNT |\
UF_WORKSTATION_TRUST_ACCOUNT |\
UF_SERVER_TRUST_ACCOUNT \
)
#define UF_SETTABLE_BITS (\
UF_SCRIPT |\
UF_ACCOUNTDISABLE |\
UF_HOMEDIR_REQUIRED |\
UF_LOCKOUT |\
UF_PASSWD_NOTREQD |\
UF_PASSWD_CANT_CHANGE |\
UF_ACCOUNT_TYPE_MASK | \
UF_DONT_EXPIRE_PASSWD | \
UF_MNS_LOGON_ACCOUNT |\
UF_ENCRYPTED_TEXT_PASSWORD_ALLOWED |\
UF_SMARTCARD_REQUIRED |\
UF_TRUSTED_FOR_DELEGATION |\
UF_NOT_DELEGATED |\
UF_USE_DES_KEY_ONLY |\
UF_DONT_REQUIRE_PREAUTH \
)
/* sAMAccountType */
#define ATYPE_NORMAL_ACCOUNT 0x30000000 /* 805306368 */
#define ATYPE_WORKSTATION_TRUST 0x30000001 /* 805306369 */
#define ATYPE_INTERDOMAIN_TRUST 0x30000002 /* 805306370 */
#define ATYPE_SECURITY_GLOBAL_GROUP 0x10000000 /* 268435456 */
#define ATYPE_DISTRIBUTION_GLOBAL_GROUP 0x10000001 /* 268435457 */
#define ATYPE_DISTRIBUTION_UNIVERSAL_GROUP ATYPE_DISTRIBUTION_GLOBAL_GROUP
#define ATYPE_SECURITY_LOCAL_GROUP 0x20000000 /* 536870912 */
#define ATYPE_DISTRIBUTION_LOCAL_GROUP 0x20000001 /* 536870913 */
#define ATYPE_ACCOUNT ATYPE_NORMAL_ACCOUNT /* 0x30000000 805306368 */
#define ATYPE_GLOBAL_GROUP ATYPE_SECURITY_GLOBAL_GROUP /* 0x10000000 268435456 */
#define ATYPE_LOCAL_GROUP ATYPE_SECURITY_LOCAL_GROUP /* 0x20000000 536870912 */
/* groupType */
#define GTYPE_SECURITY_BUILTIN_LOCAL_GROUP 0x80000005 /* -2147483643 */
#define GTYPE_SECURITY_DOMAIN_LOCAL_GROUP 0x80000004 /* -2147483644 */
#define GTYPE_SECURITY_GLOBAL_GROUP 0x80000002 /* -2147483646 */
#define GTYPE_DISTRIBUTION_GLOBAL_GROUP 0x00000002 /* 2 */
#define GTYPE_DISTRIBUTION_DOMAIN_LOCAL_GROUP 0x00000004 /* 4 */
#define GTYPE_DISTRIBUTION_UNIVERSAL_GROUP 0x00000008 /* 8 */
/* Mailslot or cldap getdcname response flags */
#define ADS_PDC 0x00000001 /* DC is PDC */
#define ADS_GC 0x00000004 /* DC is a GC of forest */
#define ADS_LDAP 0x00000008 /* DC is an LDAP server */
#define ADS_DS 0x00000010 /* DC supports DS */
#define ADS_KDC 0x00000020 /* DC is running KDC */
#define ADS_TIMESERV 0x00000040 /* DC is running time services */
#define ADS_CLOSEST 0x00000080 /* DC is closest to client */
#define ADS_WRITABLE 0x00000100 /* DC has writable DS */
#define ADS_GOOD_TIMESERV 0x00000200 /* DC has hardware clock
(and running time) */
#define ADS_NDNC 0x00000400 /* DomainName is non-domain NC serviced
by LDAP server */
#define ADS_PINGS 0x0000FFFF /* Ping response */
#define ADS_DNS_CONTROLLER 0x20000000 /* DomainControllerName is a DNS name*/
#define ADS_DNS_DOMAIN 0x40000000 /* DomainName is a DNS name */
#define ADS_DNS_FOREST 0x80000000 /* DnsForestName is a DNS name */
/* DomainCntrollerAddressType */
#define ADS_INET_ADDRESS 0x00000001
#define ADS_NETBIOS_ADDRESS 0x00000002
/* ads auth control flags */
#define ADS_AUTH_DISABLE_KERBEROS 0x01
#define ADS_AUTH_NO_BIND 0x02
#define ADS_AUTH_ANON_BIND 0x04
#define ADS_AUTH_SIMPLE_BIND 0x08
/* Kerberos environment variable names */
#define KRB5_ENV_CCNAME "KRB5CCNAME"
/* Heimdal uses a slightly different name */
#if defined(HAVE_ENCTYPE_ARCFOUR_HMAC_MD5)
#define ENCTYPE_ARCFOUR_HMAC ENCTYPE_ARCFOUR_HMAC_MD5
#endif

View File

@ -0,0 +1,38 @@
/*
* Unix SMB/CIFS implementation.
* Generic Abstract Data Types
* Copyright (C) Gerald Carter 2002.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef ADT_TREE_H
#define ADT_TREE_H
typedef struct _tree_node {
struct _tree_node *parent;
struct _tree_node **children;
int num_children;
char *key;
void *data_p;
} TREE_NODE;
typedef struct _tree_root {
TREE_NODE *root;
int (*compare)(void* x, void *y);
void (*free)(void *p);
} SORTED_TREE;
#endif

69
source4/include/asn_1.h Normal file
View File

@ -0,0 +1,69 @@
/*
Unix SMB/CIFS implementation.
simple ASN1 code
Copyright (C) Andrew Tridgell 2001
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _ASN_1_H
#define _ASN_1_H
struct nesting {
off_t start;
size_t taglen; /* for parsing */
struct nesting *next;
};
typedef struct {
uint8 *data;
size_t length;
off_t ofs;
struct nesting *nesting;
BOOL has_error;
} ASN1_DATA;
#define ASN1_APPLICATION(x) ((x)+0x60)
#define ASN1_SEQUENCE(x) ((x)+0x30)
#define ASN1_CONTEXT(x) ((x)+0xa0)
#define ASN1_GENERAL_STRING 0x1b
#define ASN1_OCTET_STRING 0x4
#define ASN1_OID 0x6
#define ASN1_BOOLEAN 0x1
#define ASN1_INTEGER 0x2
#define ASN1_ENUMERATED 0xa
#define ASN1_SET 0x31
#define ASN1_MAX_OIDS 20
/* some well known object IDs */
#define OID_SPNEGO "1 3 6 1 5 5 2"
#define OID_NTLMSSP "1 3 6 1 4 1 311 2 2 10"
#define OID_KERBEROS5_OLD "1 2 840 48018 1 2 2"
#define OID_KERBEROS5 "1 2 840 113554 1 2 2"
#define SPNEGO_NEG_RESULT_ACCEPT 0
#define SPNEGO_NEG_RESULT_INCOMPLETE 1
#define SPNEGO_NEG_RESULT_REJECT 2
/* not really ASN.1, but RFC 1964 */
#define TOK_ID_KRB_AP_REQ "\x01\x00"
#define TOK_ID_KRB_AP_REP "\x02\x00"
#define TOK_ID_KRB_ERROR "\x03\x00"
#define TOK_ID_GSS_GETMIC "\x01\x01"
#define TOK_ID_GSS_WRAP "\x02\x01"
#endif /* _ASN_1_H */

161
source4/include/auth.h Normal file
View File

@ -0,0 +1,161 @@
#ifndef _SMBAUTH_H_
#define _SMBAUTH_H_
/*
Unix SMB/CIFS implementation.
Standardised Authentication types
Copyright (C) Andrew Bartlett 2001
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* AUTH_STR - string */
typedef struct normal_string
{
int len;
char *str;
} AUTH_STR;
/* AUTH_UNISTR - unicode string or buffer */
typedef struct unicode_string
{
int len;
uchar *unistr;
} AUTH_UNISTR;
typedef struct interactive_password
{
OWF_INFO lm_owf; /* LM OWF Password */
OWF_INFO nt_owf; /* NT OWF Password */
} auth_interactive_password;
#define AUTH_FLAG_NONE 0x000000
#define AUTH_FLAG_PLAINTEXT 0x000001
#define AUTH_FLAG_LM_RESP 0x000002
#define AUTH_FLAG_NTLM_RESP 0x000004
#define AUTH_FLAG_NTLMv2_RESP 0x000008
typedef struct auth_usersupplied_info
{
DATA_BLOB lm_resp;
DATA_BLOB nt_resp;
auth_interactive_password * interactive_password;
DATA_BLOB plaintext_password;
BOOL encrypted;
uint32 auth_flags;
AUTH_STR client_domain; /* domain name string */
AUTH_STR domain; /* domain name after mapping */
AUTH_STR internal_username; /* username after mapping */
AUTH_STR smb_name; /* username before mapping */
AUTH_STR wksta_name; /* workstation name (netbios calling name) unicode string */
} auth_usersupplied_info;
#define SAM_FILL_NAME 0x01
#define SAM_FILL_INFO3 0x02
#define SAM_FILL_SAM 0x04
#define SAM_FILL_UNIX 0x08
#define SAM_FILL_ALL (SAM_FILL_NAME | SAM_FILL_INFO3 | SAM_FILL_SAM | SAM_FILL_UNIX)
typedef struct auth_serversupplied_info
{
BOOL guest;
/* This groups info is needed for when we become_user() for this uid */
int n_groups;
gid_t *groups;
/* NT group information taken from the info3 structure */
NT_USER_TOKEN *ptok;
uint8 session_key[16];
uint8 first_8_lm_hash[8];
uint32 sam_fill_level; /* How far is this structure filled? */
SAM_ACCOUNT *sam_account;
void *pam_handle;
} auth_serversupplied_info;
struct auth_context {
DATA_BLOB challenge;
/* Who set this up in the first place? */
const char *challenge_set_by;
struct auth_methods *challenge_set_method;
/* What order are the various methods in? Try to stop it changing under us */
struct auth_methods *auth_method_list;
TALLOC_CTX *mem_ctx;
const uint8 *(*get_ntlm_challenge)(struct auth_context *auth_context);
NTSTATUS (*check_ntlm_password)(const struct auth_context *auth_context,
const struct auth_usersupplied_info *user_info,
struct auth_serversupplied_info **server_info);
NTSTATUS (*nt_status_squash)(NTSTATUS nt_status);
void (*free)(struct auth_context **auth_context);
};
typedef struct auth_methods
{
struct auth_methods *prev, *next;
const char *name; /* What name got this module */
NTSTATUS (*auth)(const struct auth_context *auth_context,
void *my_private_data,
TALLOC_CTX *mem_ctx,
const struct auth_usersupplied_info *user_info,
auth_serversupplied_info **server_info);
DATA_BLOB (*get_chal)(const struct auth_context *auth_context,
void **my_private_data,
TALLOC_CTX *mem_ctx);
/* Used to keep tabs on things like the cli for SMB server authentication */
void *private_data;
/* Function to clean up the above arbitary structure */
void (*free_private_data)(void **private_data);
/* Function to send a keepalive message on the above structure */
void (*send_keepalive)(void **private_data);
} auth_methods;
typedef NTSTATUS (*auth_init_function)(struct auth_context *, const char *, struct auth_methods **);
struct auth_init_function_entry {
const char *name;
/* Function to create a member of the authmethods list */
auth_init_function init;
};
typedef struct auth_ntlmssp_state
{
TALLOC_CTX *mem_ctx;
struct auth_context *auth_context;
struct auth_serversupplied_info *server_info;
struct ntlmssp_state *ntlmssp_state;
} AUTH_NTLMSSP_STATE;
#endif /* _SMBAUTH_H_ */

175
source4/include/byteorder.h Normal file
View File

@ -0,0 +1,175 @@
/*
Unix SMB/CIFS implementation.
SMB Byte handling
Copyright (C) Andrew Tridgell 1992-1998
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _BYTEORDER_H
#define _BYTEORDER_H
/*
This file implements macros for machine independent short and
int manipulation
Here is a description of this file that I emailed to the samba list once:
> I am confused about the way that byteorder.h works in Samba. I have
> looked at it, and I would have thought that you might make a distinction
> between LE and BE machines, but you only seem to distinguish between 386
> and all other architectures.
>
> Can you give me a clue?
sure.
The distinction between 386 and other architectures is only there as
an optimisation. You can take it out completely and it will make no
difference. The routines (macros) in byteorder.h are totally byteorder
independent. The 386 optimsation just takes advantage of the fact that
the x86 processors don't care about alignment, so we don't have to
align ints on int boundaries etc. If there are other processors out
there that aren't alignment sensitive then you could also define
CAREFUL_ALIGNMENT=0 on those processors as well.
Ok, now to the macros themselves. I'll take a simple example, say we
want to extract a 2 byte integer from a SMB packet and put it into a
type called uint16 that is in the local machines byte order, and you
want to do it with only the assumption that uint16 is _at_least_ 16
bits long (this last condition is very important for architectures
that don't have any int types that are 2 bytes long)
You do this:
#define CVAL(buf,pos) (((unsigned char *)(buf))[pos])
#define PVAL(buf,pos) ((unsigned)CVAL(buf,pos))
#define SVAL(buf,pos) (PVAL(buf,pos)|PVAL(buf,(pos)+1)<<8)
then to extract a uint16 value at offset 25 in a buffer you do this:
char *buffer = foo_bar();
uint16 xx = SVAL(buffer,25);
We are using the byteoder independence of the ANSI C bitshifts to do
the work. A good optimising compiler should turn this into efficient
code, especially if it happens to have the right byteorder :-)
I know these macros can be made a bit tidier by removing some of the
casts, but you need to look at byteorder.h as a whole to see the
reasoning behind them. byteorder.h defines the following macros:
SVAL(buf,pos) - extract a 2 byte SMB value
IVAL(buf,pos) - extract a 4 byte SMB value
SVALS(buf,pos) signed version of SVAL()
IVALS(buf,pos) signed version of IVAL()
SSVAL(buf,pos,val) - put a 2 byte SMB value into a buffer
SIVAL(buf,pos,val) - put a 4 byte SMB value into a buffer
SSVALS(buf,pos,val) - signed version of SSVAL()
SIVALS(buf,pos,val) - signed version of SIVAL()
RSVAL(buf,pos) - like SVAL() but for NMB byte ordering
RSVALS(buf,pos) - like SVALS() but for NMB byte ordering
RIVAL(buf,pos) - like IVAL() but for NMB byte ordering
RIVALS(buf,pos) - like IVALS() but for NMB byte ordering
RSSVAL(buf,pos,val) - like SSVAL() but for NMB ordering
RSIVAL(buf,pos,val) - like SIVAL() but for NMB ordering
RSIVALS(buf,pos,val) - like SIVALS() but for NMB ordering
it also defines lots of intermediate macros, just ignore those :-)
*/
#undef CAREFUL_ALIGNMENT
/* we know that the 386 can handle misalignment and has the "right"
byteorder */
#ifdef __i386__
#define CAREFUL_ALIGNMENT 0
#endif
#ifndef CAREFUL_ALIGNMENT
#define CAREFUL_ALIGNMENT 1
#endif
#define CVAL(buf,pos) ((unsigned)(((const unsigned char *)(buf))[pos]))
#define CVAL_NC(buf,pos) ((unsigned)(((unsigned char *)(buf))[pos])) /* Non-const version of CVAL */
#define PVAL(buf,pos) (CVAL(buf,pos))
#define SCVAL(buf,pos,val) (CVAL_NC(buf,pos) = (val))
#if CAREFUL_ALIGNMENT
#define SVAL(buf,pos) (PVAL(buf,pos)|PVAL(buf,(pos)+1)<<8)
#define IVAL(buf,pos) (SVAL(buf,pos)|SVAL(buf,(pos)+2)<<16)
#define SSVALX(buf,pos,val) (CVAL_NC(buf,pos)=(unsigned char)((val)&0xFF),CVAL_NC(buf,pos+1)=(unsigned char)((val)>>8))
#define SIVALX(buf,pos,val) (SSVALX(buf,pos,val&0xFFFF),SSVALX(buf,pos+2,val>>16))
#define SVALS(buf,pos) ((int16)SVAL(buf,pos))
#define IVALS(buf,pos) ((int32)IVAL(buf,pos))
#define SSVAL(buf,pos,val) SSVALX((buf),(pos),((uint16)(val)))
#define SIVAL(buf,pos,val) SIVALX((buf),(pos),((uint32)(val)))
#define SSVALS(buf,pos,val) SSVALX((buf),(pos),((int16)(val)))
#define SIVALS(buf,pos,val) SIVALX((buf),(pos),((int32)(val)))
#else /* CAREFUL_ALIGNMENT */
/* this handles things for architectures like the 386 that can handle
alignment errors */
/*
WARNING: This section is dependent on the length of int16 and int32
being correct
*/
/* get single value from an SMB buffer */
#define SVAL(buf,pos) (*(const uint16 *)((const char *)(buf) + (pos)))
#define SVAL_NC(buf,pos) (*(uint16 *)((char *)(buf) + (pos))) /* Non const version of above. */
#define IVAL(buf,pos) (*(const uint32 *)((const char *)(buf) + (pos)))
#define IVAL_NC(buf,pos) (*(uint32 *)((char *)(buf) + (pos))) /* Non const version of above. */
#define SVALS(buf,pos) (*(const int16 *)((const char *)(buf) + (pos)))
#define SVALS_NC(buf,pos) (*(int16 *)((char *)(buf) + (pos))) /* Non const version of above. */
#define IVALS(buf,pos) (*(const int32 *)((const char *)(buf) + (pos)))
#define IVALS_NC(buf,pos) (*(int32 *)((char *)(buf) + (pos))) /* Non const version of above. */
/* store single value in an SMB buffer */
#define SSVAL(buf,pos,val) SVAL_NC(buf,pos)=((uint16)(val))
#define SIVAL(buf,pos,val) IVAL_NC(buf,pos)=((uint32)(val))
#define SSVALS(buf,pos,val) SVALS_NC(buf,pos)=((int16)(val))
#define SIVALS(buf,pos,val) IVALS_NC(buf,pos)=((int32)(val))
#endif /* CAREFUL_ALIGNMENT */
/* now the reverse routines - these are used in nmb packets (mostly) */
#define SREV(x) ((((x)&0xFF)<<8) | (((x)>>8)&0xFF))
#define IREV(x) ((SREV(x)<<16) | (SREV((x)>>16)))
#define RSVAL(buf,pos) SREV(SVAL(buf,pos))
#define RSVALS(buf,pos) SREV(SVALS(buf,pos))
#define RIVAL(buf,pos) IREV(IVAL(buf,pos))
#define RIVALS(buf,pos) IREV(IVALS(buf,pos))
#define RSSVAL(buf,pos,val) SSVAL(buf,pos,SREV(val))
#define RSSVALS(buf,pos,val) SSVALS(buf,pos,SREV(val))
#define RSIVAL(buf,pos,val) SIVAL(buf,pos,IREV(val))
#define RSIVALS(buf,pos,val) SIVALS(buf,pos,IREV(val))
/* Alignment macros. */
#define ALIGN4(p,base) ((p) + ((4 - (PTR_DIFF((p), (base)) & 3)) & 3))
#define ALIGN2(p,base) ((p) + ((2 - (PTR_DIFF((p), (base)) & 1)) & 1))
/* macros for accessing SMB protocol elements */
#define VWV(vwv) ((vwv)*2)
#endif /* _BYTEORDER_H */

40
source4/include/charset.h Normal file
View File

@ -0,0 +1,40 @@
/*
Unix SMB/CIFS implementation.
charset defines
Copyright (C) Andrew Tridgell 2001
Copyright (C) Jelmer Vernooij 2002
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* this defines the charset types used in samba */
typedef enum {CH_UCS2=0, CH_UNIX=1, CH_DISPLAY=2, CH_DOS=3, CH_UTF8=4} charset_t;
#define NUM_CHARSETS 5
/*
* for each charset we have a function that pulls from that charset to
* a ucs2 buffer, and a function that pushes to a ucs2 buffer
* */
struct charset_functions {
const char *name;
size_t (*pull)(void *, const char **inbuf, size_t *inbytesleft,
char **outbuf, size_t *outbytesleft);
size_t (*push)(void *, const char **inbuf, size_t *inbytesleft,
char **outbuf, size_t *outbytesleft);
struct charset_functions *prev, *next;
};

View File

@ -0,0 +1,308 @@
/*
Unix SMB/CIFS implementation.
SMB parameters and setup
Copyright (C) Andrew Tridgell 1992-1998
Copyright (C) Luke Kenneth Casson Leighton 1996-1998
Copyright (C) Jeremy Allison 1998
Copyright (C) James Myers 2003 <myersjj@samba.org>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _CLI_CONTEXT_H
#define _CLI_CONTEXT_H
struct cli_tree; /* forward declare */
struct cli_request; /* forward declare */
struct cli_session; /* forward declare */
struct cli_transport; /* forward declare */
typedef struct smb_sign_info {
void (*sign_outgoing_message)(struct cli_request *req);
BOOL (*check_incoming_message)(struct cli_request *req);
void (*free_signing_context)(struct cli_transport *transport);
void *signing_context;
BOOL doing_signing;
} smb_sign_info;
/* context that will be and has been negotiated between the client and server */
struct cli_negotiate {
/*
* negotiated maximum transmit size - this is given to us by the server
*/
unsigned max_xmit;
/* maximum number of requests that can be multiplexed */
uint16 max_mux;
/* the negotiatiated protocol */
enum protocol_types protocol;
int sec_mode; /* security mode returned by negprot */
DATA_BLOB secblob; /* cryptkey or negTokenInit blob */
uint32 sesskey;
smb_sign_info sign_info;
/* capabilities that the server reported */
uint32 capabilities;
int server_zone;
time_t server_time;
int readbraw_supported:1;
int writebraw_supported:1;
const char *server_domain;
};
/* this is the context for a SMB socket associated with the socket itself */
struct cli_socket {
TALLOC_CTX *mem_ctx; /* life of socket pool */
/* when the reference count reaches zero then the socket is destroyed */
int reference_count;
struct in_addr dest_ip;
/* the port used */
int port;
/* the open file descriptor */
int fd;
/* a count of the number of packets we have received. We
* actually only care about zero/non-zero at this stage */
unsigned pkt_count;
/* the network address of the client */
char *client_addr;
/* timeout for socket operations in milliseconds. */
int timeout;
};
/*
this structure allows applications to control the behaviour of the
client library
*/
struct cli_options {
int use_oplocks:1;
int use_level2_oplocks:1;
int use_spnego:1;
};
/* this is the context for the client transport layer */
struct cli_transport {
TALLOC_CTX *mem_ctx;
/* when the reference count reaches zero then the transport is destroyed */
int reference_count;
/* socket level info */
struct cli_socket *socket;
/* the next mid to be allocated - needed for signing and
request matching */
uint16 next_mid;
/* negotiated protocol information */
struct cli_negotiate negotiate;
/* options to control the behaviour of the client code */
struct cli_options options;
/* is a readbraw pending? we need to handle that case
specially on receiving packets */
int readbraw_pending:1;
/* an idle function - if this is defined then it will be
called once every period milliseconds while we are waiting
for a packet */
struct {
void (*func)(struct cli_transport *, void *);
void *private;
uint_t period;
} idle;
/* the error fields from the last message */
struct {
enum {ETYPE_NONE, ETYPE_DOS, ETYPE_NT, ETYPE_SOCKET, ETYPE_NBT} etype;
union {
struct {
uint8 eclass;
uint16 ecode;
} dos;
NTSTATUS nt_status;
enum socket_error socket_error;
unsigned nbt_error;
} e;
} error;
struct {
/* a oplock break request handler */
BOOL (*handler)(struct cli_transport *transport,
uint16 tid, uint16 fnum, uint8 level, void *private);
/* private data passed to the oplock handler */
void *private;
} oplock;
/* a list of async requests that are pending on this connection */
struct cli_request *pending_requests;
};
/* this is the context for the user */
/* this is the context for the session layer */
struct cli_session {
TALLOC_CTX *mem_ctx; /* life of session */
/* when the reference count reaches zero then the session is destroyed */
int reference_count;
/* transport layer info */
struct cli_transport *transport;
/* after a session setup the server provides us with
a vuid identifying the security context */
uint16 vuid;
/* default pid for this session */
uint16 pid;
};
/*
cli_tree context: internal state for a tree connection.
*/
struct cli_tree {
/* life of tree tree */
TALLOC_CTX *mem_ctx;
/* when the reference count reaches zero then the tree is destroyed */
int reference_count;
/* session layer info */
struct cli_session *session;
uint16 tid; /* tree id, aka cnum */
char *device;
char *fs_type;
};
/* the context for a single SMB request. This is passed to any request-context
* functions (similar to context.h, the server version).
* This will allow requests to be multi-threaded. */
struct cli_request {
/* allow a request to be part of a list of requests */
struct cli_request *next, *prev;
/* a talloc context for the lifetime of this request */
TALLOC_CTX *mem_ctx;
/* a request always has a transport context, nearly always has
a session context and usually has a tree context */
struct cli_transport *transport;
struct cli_session *session;
struct cli_tree *tree;
/* the flags2 from the SMB request, in raw form (host byte
order). Used to parse strings */
uint16 flags2;
/* the NT status for this request. Set by packet receive code
or code detecting error. */
NTSTATUS status;
/* the sequence number of this packet - used for signing */
unsigned seq_num;
/* set if this is a one-way request, meaning we are not
expecting a reply from the server. */
int one_way_request:1;
/* the mid of this packet - used to match replies */
uint16 mid;
struct {
/* the raw SMB buffer, including the 4 byte length header */
char *buffer;
/* the size of the raw buffer, including 4 byte header */
unsigned size;
/* how much has been allocated - on reply the buffer is over-allocated to
prevent too many realloc() calls
*/
unsigned allocated;
/* the start of the SMB header - this is always buffer+4 */
char *hdr;
/* the command words and command word count. vwv points
into the raw buffer */
char *vwv;
unsigned wct;
/* the data buffer and size. data points into the raw buffer */
char *data;
unsigned data_size;
/* ptr is used as a moving pointer into the data area
* of the packet. The reason its here and not a local
* variable in each function is that when a realloc of
* a send packet is done we need to move this
* pointer */
char *ptr;
} in, out;
/* information on what to do with a reply when it is received
asyncronously. If this is not setup when a reply is received then
the reply is discarded
The private pointer is private to the caller of the client
library (the application), not private to the library
*/
struct {
void (*fn)(struct cli_request *);
void *private;
} async;
};
/*
cli_state: internal state used in libcli library for single-threaded callers,
i.e. a single session on a single socket.
*/
struct cli_state {
TALLOC_CTX *mem_ctx; /* life of client pool */
struct cli_transport *transport;
struct cli_session *session;
struct cli_tree *tree;
struct substitute_context substitute;
};
/* useful way of catching wct errors with file and line number */
#define CLI_CHECK_MIN_WCT(req, wcount) if ((req)->in.wct < (wcount)) { \
DEBUG(1,("Unexpected WCT %d at %s(%d) - expected min %d\n", (req)->in.wct, __FILE__, __LINE__, wcount)); \
req->status = NT_STATUS_INVALID_PARAMETER; \
goto failed; \
}
#define CLI_CHECK_WCT(req, wcount) if ((req)->in.wct != (wcount)) { \
DEBUG(1,("Unexpected WCT %d at %s(%d) - expected %d\n", (req)->in.wct, __FILE__, __LINE__, wcount)); \
req->status = NT_STATUS_INVALID_PARAMETER; \
goto failed; \
}
#endif /* _CLI_CONTEXT_H */

118
source4/include/client.h Normal file
View File

@ -0,0 +1,118 @@
/*
Unix SMB/CIFS implementation.
SMB parameters and setup
Copyright (C) Andrew Tridgell 1992-1998
Copyright (C) Luke Kenneth Casson Leighton 1996-1998
Copyright (C) Jeremy Allison 1998
Copyright (C) James Myers 2003 <myersjj@samba.org>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _CLIENT_H
#define _CLIENT_H
/* the client asks for a smaller buffer to save ram and also to get more
overlap on the wire. This size gives us a nice read/write size, which
will be a multiple of the page size on almost any system */
#define CLI_BUFFER_SIZE (0xFFFF)
#define CLI_DFS_MAX_REFERRAL_LEVEL 3
#define SAFETY_MARGIN 1024
#define LARGE_WRITEX_HDR_SIZE 65
/*
* These definitions depend on smb.h
*/
typedef struct file_info
{
SMB_BIG_UINT size;
uint16 mode;
uid_t uid;
gid_t gid;
/* these times are normally kept in GMT */
time_t mtime;
time_t atime;
time_t ctime;
const char *name;
char short_name[13*3]; /* the *3 is to cope with multi-byte */
} file_info;
struct print_job_info
{
uint16 id;
uint16 priority;
size_t size;
fstring user;
fstring name;
time_t t;
};
typedef struct referral_info
{
int server_type;
int referral_flags;
int proximity;
int ttl;
int pathOffset;
int altPathOffset;
int nodeOffset;
char *path;
char *altPath;
char *node;
char *host;
char *share;
} referral_info;
typedef struct dfs_info
{
int path_consumed;
int referral_flags;
int selected_referral;
int number_referrals;
referral_info referrals[10];
} dfs_info;
/* Internal client error codes for cli_request_context.internal_error_code */
#define CLI_ERR_INVALID_TRANS_RESPONSE 100
#define DFS_MAX_CLUSTER_SIZE 8
/* client_context: used by cliraw callers to maintain Dfs
* state across multiple Dfs servers
*/
struct cli_client
{
const char* sockops;
char* username;
char* password;
char* workgroup;
TALLOC_CTX *mem_ctx;
int number_members;
BOOL use_dfs; /* True if client should support Dfs */
int connection_flags; /* see CLI_FULL_CONN.. below */
uint16 max_xmit_frag;
uint16 max_recv_frag;
struct cli_state *cli[DFS_MAX_CLUSTER_SIZE];
};
#define CLI_FULL_CONNECTION_DONT_SPNEGO 0x0001
#define CLI_FULL_CONNECTION_USE_KERBEROS 0x0002
#define CLI_FULL_CONNECTION_ANNONYMOUS_FALLBACK 0x0004
#define CLI_FULL_CONNECTION_USE_DFS 0x0008
#include "cli_context.h"
#endif /* _CLIENT_H */

41
source4/include/clitar.h Normal file
View File

@ -0,0 +1,41 @@
/*
* Unix SMB/CIFS implementation.
* clitar file format
* Copyright (C) Andrew Tridgell 2000
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
* Free Software Foundation; either version 2 of the License, or (at your
* option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License along with
* this program; if not, write to the Free Software Foundation, Inc., 675
* Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _CLITAR_H
#define _CLITAR_H
#define TBLOCK 512
#define NAMSIZ 100
union hblock {
char dummy[TBLOCK];
struct header {
char name[NAMSIZ];
char mode[8];
char uid[8];
char gid[8];
char size[12];
char mtime[12];
char chksum[8];
char linkflag;
char linkname[NAMSIZ];
} dbuf;
};
#endif /* _CLITAR_H */

346
source4/include/context.h Normal file
View File

@ -0,0 +1,346 @@
/*
Unix SMB/CIFS implementation.
Copyright (C) Andrew Tridgell 2003
Copyright (C) James J Myers 2003 <myersjj@samba.org>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/*
this header declares the core context structures associated with smb
sockets, tree connects, requests etc
the idea is that we will eventually get rid of all our global
variables and instead store our stang from structures hanging off
these basic elements
*/
/* the current user context for a request */
struct user_context {
/* the vuid is used to specify the security context for this
request. Note that this may not be the same vuid as we
received on the wire (for example, for share mode or guest
access) */
uint16 vuid;
/* the domain name, user name etc - mostly used in % substitutions */
struct userdom_struct *user;
struct user_struct *vuser;
};
/* the context for a single SMB request. This is passed to any request-context
functions */
struct request_context {
/* the server_context contains all context specific to this SMB socket */
struct server_context *smb;
/* conn is only set for operations that have a valid TID */
struct tcon_context *conn;
/* the user context is derived from the vuid plus smb.conf options */
struct user_context *user_ctx;
/* a talloc context for the lifetime of this request */
TALLOC_CTX *mem_ctx;
/* a set of flags to control usage of the request. See REQ_CONTROL_* */
unsigned control_flags;
/* the smb pid is needed for locking contexts */
uint16 smbpid;
/* the flags from the SMB request, in raw form (host byte order) */
uint16 flags, flags2;
/* the system time when the request arrived */
struct timeval request_time;
/* this can contain a fnum from an earlier part of a chained
* message (such as an SMBOpenX), or -1 */
int chained_fnum;
/* how far through the chain of SMB commands have we gone? */
unsigned chain_count;
/* the async structure allows backend functions to delay
replying to requests. To use this, the front end must set
async.send_fn to a function to be called by the backend
when the reply is finally ready to be sent. The backend
must set async.status to the status it wants in the
reply. The backend must set the REQ_CONTROL_ASYNC
control_flag on the request to indicate that it wishes to
delay the reply
If async.send_fn is NULL then the backend cannot ask for a
delayed reply for this request
note that the async.private pointer is private to the front
end not the backend. The backend must not change it.
*/
struct {
void (*send_fn)(struct request_context *);
void *private;
NTSTATUS status;
} async;
struct {
/* the raw SMB buffer, including the 4 byte length header */
char *buffer;
/* the size of the raw buffer, including 4 byte header */
unsigned size;
/* how much has been allocated - on reply the buffer is over-allocated to
prevent too many realloc() calls
*/
unsigned allocated;
/* the start of the SMB header - this is always buffer+4 */
char *hdr;
/* the command words and command word count. vwv points
into the raw buffer */
char *vwv;
unsigned wct;
/* the data buffer and size. data points into the raw buffer */
char *data;
unsigned data_size;
/* ptr is used as a moving pointer into the data area
* of the packet. The reason its here and not a local
* variable in each function is that when a realloc of
* a reply packet is done we need to move this
* pointer */
char *ptr;
} in, out;
};
/* the context associated with open files on an smb socket */
struct files_context {
struct files_struct *files; /* open files */
struct bitmap *file_bmap; /* bitmap used to allocate file handles */
/* a fsp to use when chaining */
struct files_struct *chain_fsp;
/* a fsp to use to save when breaking an oplock. */
struct files_struct *oplock_save_chain_fsp;
/* how many files are open */
int files_used;
/* limit for maximum open files */
int real_max_open_files;
};
/* the context associated with open tree connects on a smb socket */
struct tree_context {
struct tcon_context *connections;
/* number of open connections */
struct bitmap *bmap;
int num_open;
};
/* context associated with currently valid session setups */
struct users_context {
/* users from session setup */
char *session_users; /* was a pstring */
/* this holds info on user ids that are already validated for this VC */
struct user_struct *validated_users;
int next_vuid; /* initialise to VUID_OFFSET */
int num_validated_vuids;
};
/* this contains variables that should be used in % substitutions for
* smb.conf parameters */
struct substitute_context {
char *remote_arch;
/* our local netbios name, as give to us by the client */
char *local_machine;
/* the remote netbios name, as give to us by the client */
char *remote_machine;
/* the select remote protocol */
char *remote_proto;
/* the name of the client as should be displayed in
* smbstatus. Can be an IP or a netbios name */
char *client_name;
/* the username for %U */
char *user_name;
};
/* context that has been negotiated between the client and server */
struct negotiate_context {
/* have we already done the NBT session establishment? */
BOOL done_nbt_session;
/* only one negprot per connection is allowed */
BOOL done_negprot;
/* multiple session setups are allowed, but some parameters are
ignored in any but the first */
BOOL done_sesssetup;
/*
* Size of data we can send to client. Set
* by the client for all protocols above CORE.
* Set by us for CORE protocol.
*/
unsigned max_send; /* init to BUFFER_SIZE */
/*
* Size of the data we can receive. Set by us.
* Can be modified by the max xmit parameter.
*/
unsigned max_recv; /* init to BUFFER_SIZE */
/* a guess at the remote architecture. Try not to rely on this - in almost
all cases using these values is the wrong thing to do */
enum remote_arch_types ra_type;
/* the negotiatiated protocol */
enum protocol_types protocol;
/* authentication context for multi-part negprot */
struct auth_context *auth_context;
/* state of NTLMSSP auth */
struct auth_ntlmssp_state *ntlmssp_state;
/* did we tell the client we support encrypted passwords? */
BOOL encrypted_passwords;
/* did we send an extended security negprot reply? */
BOOL spnego_negotiated;
/* client capabilities */
uint32 client_caps;
};
/* this is the context for a SMB socket associated with the socket itself */
struct socket_context {
/* the open file descriptor */
int fd;
/* the last read error on the socket, if any (replaces smb_read_error global) */
int read_error;
/* a count of the number of packets we have received. We
* actually only care about zero/non-zero at this stage */
unsigned pkt_count;
/* the network address of the client */
char *client_addr;
};
/* this holds long term state specific to the printing subsystem */
struct printing_context {
struct notify_queue *notify_queue_head;
};
/* the server_context holds a linked list of pending requests,
* this is used for blocking locks and requests blocked due to oplock
* break requests */
struct pending_request {
struct pending_request *next, *prev;
/* the request itself - needs to be freed */
struct request_context *request;
};
/* the timers context contains info on when we last did various
* functions */
struct timers_context {
/* when did we last do timeout processing? */
time_t last_timeout_processing;
/* when did we last sent a keepalive */
time_t last_keepalive_sent;
/* when we last checked the smb.conf for auto-reload */
time_t last_smb_conf_reload;
};
/* the process model operations structure - contains function pointers to
the model-specific implementations of each operation */
struct model_ops {
/* called at startup when the model is selected */
void (*model_startup)(void);
/* function to accept new connection */
void (*accept_connection)(struct event_context *, struct fd_event *, time_t, uint16);
/* function to terminate a connection */
void (*terminate_connection)(struct server_context *smb, const char *reason);
/* function to exit server */
void (*exit_server)(struct server_context *smb, const char *reason);
/* returns process or thread id */
int (*get_id)(struct request_context *req);
};
/* smb context structure. This should contain all the state
* information associated with a SMB server */
struct server_context {
/* a talloc context for all data in this structure */
TALLOC_CTX *mem_ctx;
struct negotiate_context negotiate;
struct substitute_context substitute;
struct socket_context socket;
struct files_context file;
struct tree_context tree;
struct users_context users;
struct printing_context print;
struct timers_context timers;
/* the pid of the process handling this session */
pid_t pid;
/* pointer make to smbd daemon context */
struct smbd_context *smbd;
/* pointer to list of events that we are waiting on */
struct event_context *events;
/* process model specific operations */
struct model_ops *model_ops;
};

49
source4/include/debug.h Normal file
View File

@ -0,0 +1,49 @@
/*
Unix SMB/CIFS implementation.
Samba debug defines
Copyright (C) Andrew Tridgell 2003
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* the debug operations structure - contains function pointers to
various debug implementations of each operation */
struct debug_ops {
/* function to log (using DEBUG) suspicious usage of data structure */
void (*log_suspicious_usage)(const char* from, const char* info);
/* function to log (using printf) suspicious usage of data structure.
* To be used in circumstances when using DEBUG would cause loop. */
void (*print_suspicious_usage)(const char* from, const char* info);
/* function to return process/thread id */
uint32 (*get_task_id)(void);
};
void do_debug(const char *, ...) PRINTF_ATTRIBUTE(1,2);
extern int DEBUGLEVEL;
#define DEBUGLVL(level) ((level) <= DEBUGLEVEL)
#define DEBUG(level, body) do { if (DEBUGLVL(level)) do_debug body; } while (0)
#define DEBUGADD(level, body) DEBUG(level, body)
#define DEBUGC(class, level, body) DEBUG(level, body)
#define DEBUGADDC(class, level, body) DEBUG(level, body)
#define DEBUGTAB(n) do_debug_tab(n)
enum debug_logtype {DEBUG_FILE, DEBUG_STDOUT, DEBUG_STDERR};
/* keep some debug class defines for now to avoid changing old code too much */
#define DBGC_AUTH 0

View File

@ -0,0 +1,78 @@
/*
Unix SMB/CIFS implementation.
some simple double linked list macros
Copyright (C) Andrew Tridgell 1998
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* To use these macros you must have a structure containing a next and
prev pointer */
/* hook into the front of the list */
#define DLIST_ADD(list, p) \
do { \
if (!(list)) { \
(list) = (p); \
(p)->next = (p)->prev = NULL; \
} else { \
(list)->prev = (p); \
(p)->next = (list); \
(p)->prev = NULL; \
(list) = (p); \
}\
} while (0)
/* remove an element from a list - element doesn't have to be in list. */
#define DLIST_REMOVE(list, p) \
do { \
if ((p) == (list)) { \
(list) = (p)->next; \
if (list) (list)->prev = NULL; \
} else { \
if ((p)->prev) (p)->prev->next = (p)->next; \
if ((p)->next) (p)->next->prev = (p)->prev; \
} \
if ((p) && ((p) != (list))) (p)->next = (p)->prev = NULL; \
} while (0)
/* promote an element to the top of the list */
#define DLIST_PROMOTE(list, p) \
do { \
DLIST_REMOVE(list, p); \
DLIST_ADD(list, p); \
} while (0)
/* hook into the end of the list - needs a tmp pointer */
#define DLIST_ADD_END(list, p, tmp) \
do { \
if (!(list)) { \
(list) = (p); \
(p)->next = (p)->prev = NULL; \
} else { \
for ((tmp) = (list); (tmp)->next; (tmp) = (tmp)->next) ; \
(tmp)->next = (p); \
(p)->next = NULL; \
(p)->prev = (tmp); \
} \
} while (0)
/* demote an element to the end of the list, needs a tmp pointer */
#define DLIST_DEMOTE(list, p, tmp) \
do { \
DLIST_REMOVE(list, p); \
DLIST_ADD_END(list, p, tmp); \
} while (0)

233
source4/include/doserr.h Normal file
View File

@ -0,0 +1,233 @@
/*
Unix SMB/CIFS implementation.
DOS error code constants
Copyright (C) Andrew Tridgell 1992-2000
Copyright (C) John H Terpstra 1996-2000
Copyright (C) Luke Kenneth Casson Leighton 1996-2000
Copyright (C) Paul Ashton 1998-2000
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _DOSERR_H
#define _DOSERR_H
/* Error classes */
#define ERRDOS 0x01 /* Error is from the core DOS operating system set. */
#define ERRSRV 0x02 /* Error is generated by the server network file manager.*/
#define ERRHRD 0x03 /* Error is an hardware error. */
#define ERRCMD 0xFF /* Command was not in the "SMB" format. */
/* SMB X/Open error codes for the ERRDOS error class */
#define ERRsuccess 0 /* No error */
#define ERRbadfunc 1 /* Invalid function (or system call) */
#define ERRbadfile 2 /* File not found (pathname error) */
#define ERRbadpath 3 /* Directory not found */
#define ERRnofids 4 /* Too many open files */
#define ERRnoaccess 5 /* Access denied */
#define ERRbadfid 6 /* Invalid fid */
#define ERRbadmcb 7 /* Memory control blocks destroyed. */
#define ERRnomem 8 /* Out of memory */
#define ERRbadmem 9 /* Invalid memory block address */
#define ERRbadenv 10 /* Invalid environment */
#define ERRbadaccess 12 /* Invalid open mode */
#define ERRbaddata 13 /* Invalid data (only from ioctl call) */
#define ERRres 14 /* reserved */
#define ERRbaddrive 15 /* Invalid drive */
#define ERRremcd 16 /* Attempt to delete current directory */
#define ERRdiffdevice 17 /* rename/move across different filesystems */
#define ERRnofiles 18 /* no more files found in file search */
#define ERRgeneral 31 /* General failure */
#define ERRbadshare 32 /* Share mode on file conflict with open mode */
#define ERRlock 33 /* Lock request conflicts with existing lock */
#define ERRunsup 50 /* Request unsupported, returned by Win 95, RJS 20Jun98 */
#define ERRnetnamedel 64 /* Network name deleted or not available */
#define ERRnosuchshare 67 /* You specified an invalid share name */
#define ERRfilexists 80 /* File in operation already exists */
#define ERRinvalidparam 87
#define ERRcannotopen 110 /* Cannot open the file specified */
#define ERRinsufficientbuffer 122
#define ERRinvalidname 123 /* Invalid name */
#define ERRunknownlevel 124
#define ERRnotlocked 158 /* This region is not locked by this locking context. */
#define ERRrename 183
#define ERRbadpipe 230 /* Named pipe invalid */
#define ERRpipebusy 231 /* All instances of pipe are busy */
#define ERRpipeclosing 232 /* named pipe close in progress */
#define ERRnotconnected 233 /* No process on other end of named pipe */
#define ERRmoredata 234 /* More data to be returned */
#define ERRnomoreitems 259
#define ERRbaddirectory 267 /* Invalid directory name in a path. */
#define ERReasnotsupported 282 /* Extended attributes */
#define ERRlogonfailure 1326 /* Unknown username or bad password */
#define ERRbuftoosmall 2123
#define ERRunknownipc 2142
#define ERRnosuchprintjob 2151
#define ERRinvgroup 2455
/* here's a special one from observing NT */
#define ERRnoipc 66 /* don't support ipc */
/* These errors seem to be only returned by the NT printer driver system */
#define ERRdriveralreadyinstalled 1795 /* ERROR_PRINTER_DRIVER_ALREADY_INSTALLED */
#define ERRunknownprinterport 1796 /* ERROR_UNKNOWN_PORT */
#define ERRunknownprinterdriver 1797 /* ERROR_UNKNOWN_PRINTER_DRIVER */
#define ERRunknownprintprocessor 1798 /* ERROR_UNKNOWN_PRINTPROCESSOR */
#define ERRinvalidseparatorfile 1799 /* ERROR_INVALID_SEPARATOR_FILE */
#define ERRinvalidjobpriority 1800 /* ERROR_INVALID_PRIORITY */
#define ERRinvalidprintername 1801 /* ERROR_INVALID_PRINTER_NAME */
#define ERRprinteralreadyexists 1802 /* ERROR_PRINTER_ALREADY_EXISTS */
#define ERRinvalidprintercommand 1803 /* ERROR_INVALID_PRINTER_COMMAND */
#define ERRinvaliddatatype 1804 /* ERROR_INVALID_DATATYPE */
#define ERRinvalidenvironment 1805 /* ERROR_INVALID_ENVIRONMENT */
#define ERRunknownprintmonitor 3000 /* ERROR_UNKNOWN_PRINT_MONITOR */
#define ERRprinterdriverinuse 3001 /* ERROR_PRINTER_DRIVER_IN_USE */
#define ERRspoolfilenotfound 3002 /* ERROR_SPOOL_FILE_NOT_FOUND */
#define ERRnostartdoc 3003 /* ERROR_SPL_NO_STARTDOC */
#define ERRnoaddjob 3004 /* ERROR_SPL_NO_ADDJOB */
#define ERRprintprocessoralreadyinstalled 3005 /* ERROR_PRINT_PROCESSOR_ALREADY_INSTALLED */
#define ERRprintmonitoralreadyinstalled 3006 /* ERROR_PRINT_MONITOR_ALREADY_INSTALLED */
#define ERRinvalidprintmonitor 3007 /* ERROR_INVALID_PRINT_MONITOR */
#define ERRprintmonitorinuse 3008 /* ERROR_PRINT_MONITOR_IN_USE */
#define ERRprinterhasjobsqueued 3009 /* ERROR_PRINTER_HAS_JOBS_QUEUED */
/* Error codes for the ERRSRV class */
#define ERRerror 1 /* Non specific error code */
#define ERRbadpw 2 /* Bad password */
#define ERRbadtype 3 /* reserved */
#define ERRaccess 4 /* No permissions to do the requested operation */
#define ERRinvnid 5 /* tid invalid */
#define ERRinvnetname 6 /* Invalid servername */
#define ERRinvdevice 7 /* Invalid device */
#define ERRqfull 49 /* Print queue full */
#define ERRqtoobig 50 /* Queued item too big */
#define ERRinvpfid 52 /* Invalid print file in smb_fid */
#define ERRsmbcmd 64 /* Unrecognised command */
#define ERRsrverror 65 /* smb server internal error */
#define ERRfilespecs 67 /* fid and pathname invalid combination */
#define ERRbadlink 68 /* reserved */
#define ERRbadpermits 69 /* Access specified for a file is not valid */
#define ERRbadpid 70 /* reserved */
#define ERRsetattrmode 71 /* attribute mode invalid */
#define ERRpaused 81 /* Message server paused */
#define ERRmsgoff 82 /* Not receiving messages */
#define ERRnoroom 83 /* No room for message */
#define ERRrmuns 87 /* too many remote usernames */
#define ERRtimeout 88 /* operation timed out */
#define ERRnoresource 89 /* No resources currently available for request. */
#define ERRtoomanyuids 90 /* too many userids */
#define ERRbaduid 91 /* bad userid */
#define ERRuseMPX 250 /* temporarily unable to use raw mode, use MPX mode */
#define ERRuseSTD 251 /* temporarily unable to use raw mode, use standard mode */
#define ERRcontMPX 252 /* resume MPX mode */
#define ERRbadPW /* reserved */
#define ERRnosupport 0xFFFF
#define ERRunknownsmb 22 /* from NT 3.5 response */
/* Error codes for the ERRHRD class */
#define ERRnowrite 19 /* read only media */
#define ERRbadunit 20 /* Unknown device */
#define ERRnotready 21 /* Drive not ready */
#define ERRbadcmd 22 /* Unknown command */
#define ERRdata 23 /* Data (CRC) error */
#define ERRbadreq 24 /* Bad request structure length */
#define ERRseek 25
#define ERRbadmedia 26
#define ERRbadsector 27
#define ERRnopaper 28
#define ERRwrite 29 /* write fault */
#define ERRread 30 /* read fault */
#define ERRgeneral 31 /* General hardware failure */
#define ERRwrongdisk 34
#define ERRFCBunavail 35
#define ERRsharebufexc 36 /* share buffer exceeded */
#define ERRdiskfull 39
/* these are win32 error codes. There are only a few places where
these matter for Samba, primarily in the NT printing code */
#define WERR_OK W_ERROR(0)
#define WERR_BADFUNC W_ERROR(1)
#define WERR_BADFILE W_ERROR(2)
#define WERR_ACCESS_DENIED W_ERROR(5)
#define WERR_BADFID W_ERROR(6)
#define WERR_NOMEM W_ERROR(8)
#define WERR_GENERAL_FAILURE W_ERROR(31)
#define WERR_NOT_SUPPORTED W_ERROR(50)
#define WERR_PRINTQ_FULL W_ERROR(61)
#define WERR_NO_SPOOL_SPACE W_ERROR(62)
#define WERR_NO_SUCH_SHARE W_ERROR(67)
#define WERR_ALREADY_EXISTS W_ERROR(80)
#define WERR_BAD_PASSWORD W_ERROR(86)
#define WERR_INVALID_PARAM W_ERROR(87)
#define WERR_INSUFFICIENT_BUFFER W_ERROR(122)
#define WERR_INVALID_NAME W_ERROR(123)
#define WERR_UNKNOWN_LEVEL W_ERROR(124)
#define WERR_OBJECT_PATH_INVALID W_ERROR(161)
#define WERR_NO_MORE_ITEMS W_ERROR(259)
#define WERR_MORE_DATA W_ERROR(234)
#define WERR_INVALID_OWNER W_ERROR(1307)
#define WERR_CAN_NOT_COMPLETE W_ERROR(1003)
#define WERR_INVALID_SECURITY_DESCRIPTOR W_ERROR(1338)
#define WERR_SERVER_UNAVAILABLE W_ERROR(1722)
#define WERR_INVALID_FORM_NAME W_ERROR(1902)
#define WERR_INVALID_FORM_SIZE W_ERROR(1903)
#define WERR_BUF_TOO_SMALL W_ERROR(2123)
#define WERR_JOB_NOT_FOUND W_ERROR(2151)
#define WERR_DEST_NOT_FOUND W_ERROR(2152)
#define WERR_NOT_LOCAL_DOMAIN W_ERROR(2320)
#define WERR_STATUS_MORE_ENTRIES W_ERROR(0x0105)
#define WERR_PRINTER_DRIVER_ALREADY_INSTALLED W_ERROR(ERRdriveralreadyinstalled)
#define WERR_UNKNOWN_PORT W_ERROR(ERRunknownprinterport)
#define WERR_UNKNOWN_PRINTER_DRIVER W_ERROR(ERRunknownprinterdriver)
#define WERR_UNKNOWN_PRINTPROCESSOR W_ERROR(ERRunknownprintprocessor)
#define WERR_INVALID_SEPARATOR_FILE W_ERROR(ERRinvalidseparatorfile)
#define WERR_INVALID_PRIORITY W_ERROR(ERRinvalidjobpriority)
#define WERR_INVALID_PRINTER_NAME W_ERROR(ERRinvalidprintername)
#define WERR_PRINTER_ALREADY_EXISTS W_ERROR(ERRprinteralreadyexists)
#define WERR_INVALID_PRINTER_COMMAND W_ERROR(ERRinvalidprintercommand)
#define WERR_INVALID_DATATYPE W_ERROR(ERRinvaliddatatype)
#define WERR_INVALID_ENVIRONMENT W_ERROR(ERRinvalidenvironment)
#define WERR_UNKNOWN_PRINT_MONITOR W_ERROR(ERRunknownprintmonitor)
#define WERR_PRINTER_DRIVER_IN_USE W_ERROR(ERRprinterdriverinuse)
#define WERR_SPOOL_FILE_NOT_FOUND W_ERROR(ERRspoolfilenotfound)
#define WERR_SPL_NO_STARTDOC W_ERROR(ERRnostartdoc)
#define WERR_SPL_NO_ADDJOB W_ERROR(ERRnoaddjob)
#define WERR_PRINT_PROCESSOR_ALREADY_INSTALLED W_ERROR(ERRprintprocessoralreadyinstalled)
#define WERR_PRINT_MONITOR_ALREADY_INSTALLED W_ERROR(ERRprintmonitoralreadyinstalled)
#define WERR_INVALID_PRINT_MONITOR W_ERROR(ERRinvalidprintmonitor)
#define WERR_PRINT_MONITOR_IN_USE W_ERROR(ERRprintmonitorinuse)
#define WERR_PRINTER_HAS_JOBS_QUEUED W_ERROR(ERRprinterhasjobsqueued)
/* DFS errors */
#ifndef NERR_BASE
#define NERR_BASE (2100)
#endif
#define WERR_DFS_NO_SUCH_VOL W_ERROR(NERR_BASE+562)
#define WERR_DFS_NO_SUCH_SHARE W_ERROR(NERR_BASE+565)
#define WERR_DFS_NO_SUCH_SERVER W_ERROR(NERR_BASE+573)
#define WERR_DFS_INTERNAL_ERROR W_ERROR(NERR_BASE+590)
#define WERR_DFS_CANT_CREATE_JUNCT W_ERROR(NERR_BASE+569)
#endif /* _DOSERR_H */

View File

@ -0,0 +1,39 @@
/*
Unix SMB/CIFS implementation.
Copyright (C) 2001 by Martin Pool <mbp@samba.org>
Copyright (C) 2003 by Anthony Liguori <aliguor@us.ibm.com>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/**
* @file dynconfig.h
*
* @brief Exported global configurations.
**/
extern char const *dyn_SBINDIR,
*dyn_BINDIR,
*dyn_SWATDIR;
extern pstring dyn_CONFIGFILE;
extern const char *dyn_LOGFILEBASE;
extern pstring dyn_LMHOSTSFILE;
extern pstring dyn_LIBDIR;
extern const fstring dyn_SHLIBEXT;
extern const pstring dyn_LOCKDIR;
extern const pstring dyn_PIDDIR;
extern const pstring dyn_SMB_PASSWD_FILE;
extern const pstring dyn_PRIVATE_DIR;

64
source4/include/enums.h Normal file
View File

@ -0,0 +1,64 @@
/*
Unix SMB/CIFS implementation.
Copyright (C) Andrew Tridgell 2003
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/*
this header declares basic enumerated types
*/
/* protocol types. It assumes that higher protocols include lower protocols
as subsets */
enum protocol_types {PROTOCOL_NONE,PROTOCOL_CORE,PROTOCOL_COREPLUS,PROTOCOL_LANMAN1,PROTOCOL_LANMAN2,PROTOCOL_NT1};
/* security levels */
enum security_types {SEC_SHARE,SEC_USER,SEC_SERVER,SEC_DOMAIN,SEC_ADS};
/* server roles */
enum server_types
{
ROLE_STANDALONE,
ROLE_DOMAIN_MEMBER,
ROLE_DOMAIN_BDC,
ROLE_DOMAIN_PDC
};
/* printing types */
enum printing_types {PRINT_BSD,PRINT_SYSV,PRINT_AIX,PRINT_HPUX,
PRINT_QNX,PRINT_PLP,PRINT_LPRNG,PRINT_SOFTQ,
PRINT_CUPS,PRINT_LPRNT,PRINT_LPROS2
#ifdef DEVELOPER
,PRINT_TEST,PRINT_VLP
#endif /* DEVELOPER */
};
/* LDAP schema types */
enum schema_types {SCHEMA_COMPAT, SCHEMA_AD, SCHEMA_SAMBA};
/* LDAP SSL options */
enum ldap_ssl_types {LDAP_SSL_ON, LDAP_SSL_OFF, LDAP_SSL_START_TLS};
/* LDAP PASSWD SYNC methods */
enum ldap_passwd_sync_types {LDAP_PASSWD_SYNC_ON, LDAP_PASSWD_SYNC_OFF, LDAP_PASSWD_SYNC_ONLY};
/* Remote architectures we know about. */
enum remote_arch_types {RA_UNKNOWN, RA_WFWG, RA_OS2, RA_WIN95, RA_WINNT, RA_WIN2K, RA_WINXP, RA_SAMBA};
/* case handling */
enum case_handling {CASE_LOWER,CASE_UPPER};

75
source4/include/events.h Normal file
View File

@ -0,0 +1,75 @@
/*
Unix SMB/CIFS implementation.
main select loop and event handling
Copyright (C) Andrew Tridgell 2003
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/*
please read the comments in events.c before modifying
*/
struct event_context {
/* list of filedescriptor events */
struct fd_event {
struct fd_event *next, *prev;
int fd;
uint16 flags; /* see EVENT_FD_* flags */
void (*handler)(struct event_context *ev, struct fd_event *fde, time_t t, uint16 flags);
void *private;
int ref_count;
} *fd_events;
/* list of timed events */
struct timed_event {
struct timed_event *next, *prev;
time_t next_event;
void (*handler)(struct event_context *ev, struct timed_event *te, time_t t);
void *private;
int ref_count;
} *timed_events;
/* list of loop events - called on each select() */
struct loop_event {
struct loop_event *next, *prev;
void (*handler)(struct event_context *ev, struct loop_event *le, time_t t);
void *private;
int ref_count;
} *loop_events;
/* list of signal events */
struct signal_event {
struct signal_event *next, *prev;
int signum;
void (*handler)(struct event_context *ev, struct signal_event *se, int signum, void *sigarg);
void *private;
int ref_count;
} *signal_events;
/* the maximum file descriptor number in fd_events */
int maxfd;
/* information for exiting from the event loop */
struct {
BOOL exit_now;
int code;
} exit;
};
/* bits for fd_event.flags */
#define EVENT_FD_READ 1
#define EVENT_FD_WRITE 2

View File

@ -0,0 +1,78 @@
/*
Copyright (C) Andrew Tridgell <genstruct@tridgell.net> 2002
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _GENPARSER_H
#define _GENPARSER_H
/* these macros are needed for genstruct auto-parsers */
#ifndef GENSTRUCT
#define GENSTRUCT
#define _LEN(x)
#define _NULLTERM
#endif
/*
automatic marshalling/unmarshalling system for C structures
*/
/* flag to mark a fixed size array as actually being null terminated */
#define FLAG_NULLTERM 1
#define FLAG_ALWAYS 2
struct enum_struct {
const char *name;
unsigned value;
};
/* intermediate dumps are stored in one of these */
struct parse_string {
unsigned allocated;
unsigned length;
char *s;
};
typedef int (*gen_dump_fn)(TALLOC_CTX *, struct parse_string *, const char *ptr, unsigned indent);
typedef int (*gen_parse_fn)(TALLOC_CTX *, char *ptr, const char *str);
/* genstruct.pl generates arrays of these */
struct parse_struct {
const char *name;
unsigned ptr_count;
unsigned size;
unsigned offset;
unsigned array_len;
const char *dynamic_len;
unsigned flags;
gen_dump_fn dump_fn;
gen_parse_fn parse_fn;
};
#define DUMP_PARSE_DECL(type) \
int gen_dump_ ## type(TALLOC_CTX *, struct parse_string *, const char *, unsigned); \
int gen_parse_ ## type(TALLOC_CTX *, char *, const char *);
DUMP_PARSE_DECL(char)
DUMP_PARSE_DECL(int)
DUMP_PARSE_DECL(unsigned)
DUMP_PARSE_DECL(double)
DUMP_PARSE_DECL(float)
#define gen_dump_unsigned_char gen_dump_char
#define gen_parse_unsigned_char gen_parse_char
#endif /* _GENPARSER_H */

View File

@ -0,0 +1,58 @@
/*
Copyright (C) Simo Sorce <idra@samba.org> 2002
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _GENPARSER_SAMBA_H
#define _GENPARSER_SAMBA_H
const struct parse_struct pinfo_security_ace_info[] = {
{"type", 0, sizeof(uint8), offsetof(struct security_ace_info, type), 0, NULL, 0, gen_dump_uint8, gen_parse_uint8},
{"flags", 0, sizeof(uint8), offsetof(struct security_ace_info, flags), 0, NULL, 0, gen_dump_uint8, gen_parse_uint8},
{"size", 0, sizeof(uint16), offsetof(struct security_ace_info, size), 0, NULL, 0, gen_dump_uint16, gen_parse_uint16},
{"info", 0, sizeof(char), offsetof(struct security_ace_info, info), 0, NULL, 0, gen_dump_SEC_ACCESS, gen_parse_SEC_ACCESS},
{"obj_flags", 0, sizeof(uint32), offsetof(struct security_ace_info, obj_flags), 0, NULL, 0, gen_dump_uint32, gen_parse_uint32},
{"obj_guid", 0, sizeof(char), offsetof(struct security_ace_info, obj_guid), 0, NULL, 0, gen_dump_GUID, gen_parse_GUID},
{"inh_guid", 0, sizeof(char), offsetof(struct security_ace_info, inh_guid), 0, NULL, 0, gen_dump_GUID, gen_parse_GUID},
{"trustee", 0, sizeof(char), offsetof(struct security_ace_info, trustee), 0, NULL, 0, gen_dump_DOM_SID, gen_parse_DOM_SID},
{NULL, 0, 0, 0, 0, NULL, 0, NULL, NULL}};
const struct parse_struct pinfo_security_acl_info[] = {
{"revision", 0, sizeof(uint16), offsetof(struct security_acl_info, revision), 0, NULL, 0, gen_dump_uint16, gen_parse_uint16},
{"size", 0, sizeof(uint16), offsetof(struct security_acl_info, size), 0, NULL, 0, gen_dump_uint16, gen_parse_uint16},
{"num_aces", 0, sizeof(uint32), offsetof(struct security_acl_info, num_aces), 0, NULL, 0, gen_dump_uint32, gen_parse_uint32},
{"ace", 1, sizeof(struct security_ace_info), offsetof(struct security_acl_info, ace), 0, "size", 0, gen_dump_SEC_ACE, gen_parse_SEC_ACE},
{NULL, 0, 0, 0, 0, NULL, 0, NULL, NULL}};
const struct parse_struct pinfo_security_descriptor_info[] = {
{"revision", 0, sizeof(uint16), offsetof(struct security_descriptor_info, revision), 0, NULL, 0, gen_dump_uint16, gen_parse_uint16},
{"type", 0, sizeof(uint16), offsetof(struct security_descriptor_info, type), 0, NULL, 0, gen_dump_uint16, gen_parse_uint16},
{"off_owner_sid", 0, sizeof(uint32), offsetof(struct security_descriptor_info, off_owner_sid), 0, NULL, 0, gen_dump_uint32, gen_parse_uint32},
{"off_grp_sid", 0, sizeof(uint32), offsetof(struct security_descriptor_info, off_grp_sid), 0, NULL, 0, gen_dump_uint32, gen_parse_uint32},
{"off_sacl", 0, sizeof(uint32), offsetof(struct security_descriptor_info, off_sacl), 0, NULL, 0, gen_dump_uint32, gen_parse_uint32},
{"off_dacl", 0, sizeof(uint32), offsetof(struct security_descriptor_info, off_dacl), 0, NULL, 0, gen_dump_uint32, gen_parse_uint32},
{"dacl", 1, sizeof(struct security_acl_info), offsetof(struct security_descriptor_info, dacl), 0, NULL, 0, gen_dump_SEC_ACL, gen_parse_SEC_ACL},
{"sacl", 1, sizeof(struct security_acl_info), offsetof(struct security_descriptor_info, sacl), 0, NULL, 0, gen_dump_SEC_ACL, gen_parse_SEC_ACL},
{"owner_sid", 1, sizeof(char), offsetof(struct security_descriptor_info, owner_sid), 0, NULL, 0, gen_dump_DOM_SID, gen_parse_DOM_SID},
{"grp_sid", 1, sizeof(char), offsetof(struct security_descriptor_info, grp_sid), 0, NULL, 0, gen_dump_DOM_SID, gen_parse_DOM_SID},
{NULL, 0, 0, 0, 0, NULL, 0, NULL, NULL}};
const struct parse_struct pinfo_luid_attr_info[] = {
{"attr", 0, sizeof(uint32), offsetof(struct LUID_ATTR, attr), 0, NULL, 0, gen_dump_uint32, gen_parse_uint32},
{"luid", 1, sizeof(LUID), offsetof(struct LUID_ATTR, luid), 0, NULL, 0, gen_dump_LUID, gen_parse_LUID},
{NULL, 0, 0, 0, 0, NULL, 0, NULL, NULL}};
#endif /* _GENPARSER_SAMBA_H */

230
source4/include/gums.h Normal file
View File

@ -0,0 +1,230 @@
/*
Unix SMB/CIFS implementation.
GUMS structures
Copyright (C) Simo Sorce 2002
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _GUMS_H
#define _GUMS_H
#define GUMS_VERSION_MAJOR 0
#define GUMS_VERSION_MINOR 1
#define GUMS_OBJECT_VERSION 1
#define GUMS_OBJ_DOMAIN 1
#define GUMS_OBJ_NORMAL_USER 2
#define GUMS_OBJ_GROUP 3
#define GUMS_OBJ_ALIAS 4
#define GUMS_OBJ_WORKSTATION_TRUST 5
#define GUMS_OBJ_SERVER_TRUST 6
#define GUMS_OBJ_DOMAIN_TRUST 7
typedef struct gums_user
{
DOM_SID *group_sid; /* Primary Group SID */
NTTIME logon_time; /* logon time */
NTTIME logoff_time; /* logoff time */
NTTIME kickoff_time; /* kickoff time */
NTTIME pass_last_set_time; /* password last set time */
NTTIME pass_can_change_time; /* password can change time */
NTTIME pass_must_change_time; /* password must change time */
char *full_name; /* user's full name string */
char *home_dir; /* home directory string */
char *dir_drive; /* home directory drive string */
char *logon_script; /* logon script string */
char *profile_path; /* profile path string */
char *workstations; /* login from workstations string */
char *unknown_str; /* don't know what this is, yet. */
char *munged_dial; /* munged path name and dial-back tel number */
DATA_BLOB lm_pw; /* .data is Null if no password */
DATA_BLOB nt_pw; /* .data is Null if no password */
uint32 unknown_3; /* 0x00ff ffff */
uint16 logon_divs; /* 168 - number of hours in a week */
uint32 hours_len; /* normally 21 bytes */
uint8 *hours;
uint32 unknown_5; /* 0x0002 0000 */
uint32 unknown_6; /* 0x0000 04ec */
} GUMS_USER;
typedef struct gums_group
{
uint32 count; /* Number of SIDs */
DOM_SID **members; /* SID array */
} GUMS_GROUP;
union gums_obj_p {
gums_user *user;
gums_group *group;
}
typedef struct gums_object
{
TALLOC_CTX *mem_ctx;
uint32 type; /* Object Type */
uint32 version; /* Object Version */
uint32 seq_num; /* Object Sequence Number */
SEC_DESC *sec_desc; /* Security Descriptor */
DOM_SID *sid; /* Object Sid */
char *name; /* Object Name */
char *description; /* Object Description */
union gums_obj_p data; /* Object Specific data */
} GUMS_OBJECT;
typedef struct gums_data_set
{
int type; /* GUMS_SET_xxx */
void *data;
} GUMS_DATA_SET;
typedef struct gums_commit_set
{
TALLOC_CTX *mem_ctx;
uint32 type; /* Object type */
DOM_SID sid; /* Object Sid */
uint32 count; /* number of changes */
GUMS_DATA_SET **data;
} GUMS_COMMIT_SET;
typedef struct gums_privilege
{
TALLOC_CTX *mem_ctx;
uint32 type; /* Object Type */
uint32 version; /* Object Version */
uint32 seq_num; /* Object Sequence Number */
LUID_ATTR *privilege; /* Privilege Type */
char *name; /* Object Name */
char *description; /* Object Description */
uint32 count;
DOM_SID **members;
} GUMS_PRIVILEGE;
typedef struct gums_functions
{
/* Generic object functions */
NTSTATUS (*get_domain_sid) (DOM_SID **sid, const char* name);
NTSTATUS (*set_domain_sid) (const DOM_SID *sid);
NTSTATUS (*get_sequence_number) (void);
NTSTATUS (*new_object) (DOM_SID **sid, const char *name, const int obj_type);
NTSTATUS (*delete_object) (const DOM_SID *sid);
NTSTATUS (*get_object_from_sid) (GUMS_OBJECT **object, const DOM_SID *sid, const int obj_type);
NTSTATUS (*get_sid_from_name) (GUMS_OBJECT **object, const char *name);
/* This function is used to get the list of all objects changed since b_time, it is
used to support PDC<->BDC synchronization */
NTSTATUS (*get_updated_objects) (GUMS_OBJECT **objects, const NTTIME base_time);
NTSTATUS (*enumerate_objects_start) (void *handle, const DOM_SID *sid, const int obj_type);
NTSTATUS (*enumerate_objects_get_next) (GUMS_OBJECT **object, void *handle);
NTSTATUS (*enumerate_objects_stop) (void *handle);
/* This function MUST be used ONLY by PDC<->BDC replication code or recovery tools.
Never use this function to update an object in the database, use set_object_values() */
NTSTATUS (*set_object) (const GUMS_OBJECT *object);
/* set object values function */
NTSTATUS (*set_object_values) (DOM_SID *sid, uint32 count, GUMS_DATA_SET *data_set);
/* Group related functions */
NTSTATUS (*add_memberss_to_group) (const DOM_SID *group, const DOM_SID **members);
NTSTATUS (*delete_members_from_group) (const DOM_SID *group, const DOM_SID **members);
NTSTATUS (*enumerate_group_members) (DOM_SID **members, const DOM_SID *sid, const int type);
NTSTATUS (*get_sid_groups) (DOM_SID **groups, const DOM_SID *sid);
NTSTATUS (*lock_sid) (const DOM_SID *sid);
NTSTATUS (*unlock_sid) (const DOM_SID *sid);
/* privileges related functions */
NTSTATUS (*add_members_to_privilege) (const LUID_ATTR *priv, const DOM_SID **members);
NTSTATUS (*delete_members_from_privilege) (const LUID_ATTR *priv, const DOM_SID **members);
NTSTATUS (*enumerate_privilege_members) (DOM_SID **members, const LUID_ATTR *priv);
NTSTATUS (*get_sid_privileges) (DOM_SID **privs, const DOM_SID *sid);
/* warning!: set_privilege will overwrite a prior existing privilege if such exist */
NTSTATUS (*set_privilege) (GUMS_PRIVILEGE *priv);
} GUMS_FUNCTIONS;
/* define value types */
#define GUMS_SET_PRIMARY_GROUP 1
#define GUMS_SET_SEC_DESC 2
/* user specific type values */
#define GUMS_SET_LOGON_TIME 10 /* keep NTTIME consecutive */
#define GUMS_SET_LOGOFF_TIME 11 /* too ease checking */
#define GUMS_SET_KICKOFF_TIME 13
#define GUMS_SET_PASS_LAST_SET_TIME 14
#define GUMS_SET_PASS_CAN_CHANGE_TIME 15
#define GUMS_SET_PASS_MUST_CHANGE_TIME 16 /* NTTIME end */
#define GUMS_SET_NAME 20 /* keep strings consecutive */
#define GUMS_SET_DESCRIPTION 21 /* too ease checking */
#define GUMS_SET_FULL_NAME 22
#define GUMS_SET_HOME_DIRECTORY 23
#define GUMS_SET_DRIVE 24
#define GUMS_SET_LOGON_SCRIPT 25
#define GUMS_SET_PROFILE_PATH 26
#define GUMS_SET_WORKSTATIONS 27
#define GUMS_SET_UNKNOWN_STRING 28
#define GUMS_SET_MUNGED_DIAL 29 /* strings end */
#define GUMS_SET_LM_PASSWORD 40
#define GUMS_SET_NT_PASSWORD 41
#define GUMS_SET_PLAINTEXT_PASSWORD 42
#define GUMS_SET_UNKNOWN_3 43
#define GUMS_SET_LOGON_DIVS 44
#define GUMS_SET_HOURS_LEN 45
#define GUMS_SET_HOURS 46
#define GUMS_SET_UNKNOWN_5 47
#define GUMS_SET_UNKNOWN_6 48
#define GUMS_SET_MUST_CHANGE_PASS 50
#define GUMS_SET_CANNOT_CHANGE_PASS 51
#define GUMS_SET_PASS_NEVER_EXPIRE 52
#define GUMS_SET_ACCOUNT_DISABLED 53
#define GUMS_SET_ACCOUNT_LOCKOUT 54
/*group specific type values */
#define GUMS_ADD_SID_LIST 60
#define GUMS_DEL_SID_LIST 61
#define GUMS_SET_SID_LIST 62
#endif /* _GUMS_H */

32
source4/include/hmacmd5.h Normal file
View File

@ -0,0 +1,32 @@
/*
Unix SMB/CIFS implementation.
Interface header: Scheduler service
Copyright (C) Luke Kenneth Casson Leighton 1996-1999
Copyright (C) Andrew Tridgell 1992-1999
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _HMAC_MD5_H
typedef struct
{
struct MD5Context ctx;
uchar k_ipad[65];
uchar k_opad[65];
} HMACMD5Context;
#endif /* _HMAC_MD5_H */

1237
source4/include/includes.h Normal file

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,12 @@
/*
This structure is used by lib/interfaces.c to return the list of network
interfaces on the machine
*/
#define MAX_INTERFACES 128
struct iface_struct {
char name[16];
struct in_addr ip;
struct in_addr netmask;
};

24
source4/include/intl.h Normal file
View File

@ -0,0 +1,24 @@
/*
Unix SMB/CIFS implementation.
internationalisation headers
Copyright (C) Andrew Tridgell 2001
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* ideally we would have a static mapping, but that precludes
dynamic loading. This is a reasonable compromise */
#define _(x) lang_msg_rotate(x)

30
source4/include/ioctl.h Normal file
View File

@ -0,0 +1,30 @@
/*
Unix SMB/CIFS implementation.
ioctl and fsctl definitions
Copyright (C) Andrew Tridgell 2003
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* ioctl codes */
#define IOCTL_QUERY_JOB_INFO 0x530060
/* filesystem control codes */
#define FSCTL_FILESYSTEM 0x90000
#define FSCTL_SET_SPARSE (FSCTL_FILESYSTEM | 0xc4)

View File

@ -0,0 +1,67 @@
#ifndef _LIBSMB_INTERNAL_H_
#define _LIBSMB_INTERNAL_H_
#define SMBC_MAX_NAME 1023
#define SMBC_FILE_MODE (S_IFREG | 0444)
#define SMBC_DIR_MODE (S_IFDIR | 0555)
#include "../include/libsmbclient.h"
struct _SMBCSRV {
struct cli_state cli;
dev_t dev;
BOOL no_pathinfo2;
int server_fd;
SMBCSRV *next, *prev;
};
/*
* Keep directory entries in a list
*/
struct smbc_dir_list {
struct smbc_dir_list *next;
struct smbc_dirent *dirent;
};
/*
* Structure for open file management
*/
struct _SMBCFILE {
int cli_fd;
char *fname;
off_t offset;
struct _SMBCSRV *srv;
BOOL file;
struct smbc_dir_list *dir_list, *dir_end, *dir_next;
int dir_type, dir_error;
SMBCFILE *next, *prev;
};
struct smbc_internal_data {
/** INTERNAL: is this handle initialized ?
*/
int _initialized;
/** INTERNAL: dirent pointer location
*/
char _dirent[512];
/** INTERNAL: server connection list
*/
SMBCSRV * _servers;
/** INTERNAL: open file/dir list
*/
SMBCFILE * _files;
};
#endif

File diff suppressed because it is too large Load Diff

226
source4/include/local.h Normal file
View File

@ -0,0 +1,226 @@
/* Copyright (C) 1995-1998 Samba-Team */
/* Copyright (C) 1998 John H Terpstra <jht@aquasoft.com.au> */
/* local definitions for file server */
#ifndef _LOCAL_H
#define _LOCAL_H
/* The default workgroup - usually overridden in smb.conf */
#ifndef DEFAULT_WORKGROUP
#define DEFAULT_WORKGROUP "WORKGROUP"
#endif
/* the maximum debug level to compile into the code. This assumes a good
optimising compiler that can remove unused code
for embedded or low-memory systems set this to a value like 2 to get
only important messages. This gives *much* smaller binaries
*/
#ifndef MAX_DEBUG_LEVEL
#define MAX_DEBUG_LEVEL 1000
#endif
/* This defines the section name in the configuration file that will contain */
/* global parameters - that is, parameters relating to the whole server, not */
/* just services. This name is then reserved, and may not be used as a */
/* a service name. It will default to "global" if not defined here. */
#define GLOBAL_NAME "global"
#define GLOBAL_NAME2 "globals"
/* This defines the section name in the configuration file that will
refer to the special "homes" service */
#define HOMES_NAME "homes"
/* This defines the section name in the configuration file that will
refer to the special "printers" service */
#define PRINTERS_NAME "printers"
/* Yves Gaige <yvesg@hptnodur.grenoble.hp.com> requested this set this */
/* to a maximum of 8 if old smb clients break because of long printer names. */
#define MAXPRINTERLEN 15
/* max number of directories open at once */
/* note that with the new directory code this no longer requires a
file handle per directory, but large numbers do use more memory */
#define MAX_OPEN_DIRECTORIES 256
/* max number of directory handles */
/* As this now uses the bitmap code this can be
quite large. */
#define MAX_DIRECTORY_HANDLES 2048
/* maximum number of file caches per smbd */
#define MAX_WRITE_CACHES 10
/* define what facility to use for syslog */
#ifndef SYSLOG_FACILITY
#define SYSLOG_FACILITY LOG_DAEMON
#endif
/*
* Default number of maximum open files per smbd. This is
* also limited by the maximum available file descriptors
* per process and can also be set in smb.conf as "max open files"
* in the [global] section.
*/
#ifndef MAX_OPEN_FILES
#define MAX_OPEN_FILES 10000
#endif
#define WORDMAX 0xFFFF
/* the maximum password length before we declare a likely attack */
#define MAX_PASS_LEN 200
/* separators for lists */
#define LIST_SEP " \t,;\n\r"
/* wchar separators for lists */
#define LIST_SEP_W wchar_list_sep
/* this is where browse lists are kept in the lock dir */
#define SERVER_LIST "browse.dat"
/* shall filenames with illegal chars in them get mangled in long
filename listings? */
#define MANGLE_LONG_FILENAMES
/* define this if you want to stop spoofing with .. and soft links
NOTE: This also slows down the server considerably */
#define REDUCE_PATHS
/* the size of the directory cache */
#define DIRCACHESIZE 20
/* what default type of filesystem do we want this to show up as in a
NT file manager window? */
#define FSTYPE_STRING "NTFS"
/* the default guest account - normally set in the Makefile or smb.conf */
#ifndef GUEST_ACCOUNT
#define GUEST_ACCOUNT "nobody"
#endif
/* user to test password server with as invalid in security=server mode. */
#ifndef INVALID_USER_PREFIX
#define INVALID_USER_PREFIX "sambatest"
#endif
/* the default pager to use for the client "more" command. Users can
override this with the PAGER environment variable */
#ifndef PAGER
#define PAGER "more"
#endif
/* the size of the uid cache used to reduce valid user checks */
#define VUID_CACHE_SIZE 32
/* the following control timings of various actions. Don't change
them unless you know what you are doing. These are all in seconds */
#define DEFAULT_SMBD_TIMEOUT (60*60*24*7)
#define SMBD_RELOAD_CHECK (180)
#define IDLE_CLOSED_TIMEOUT (60)
#define DPTR_IDLE_TIMEOUT (120)
#define SMBD_SELECT_TIMEOUT (60)
#define NMBD_SELECT_LOOP (10)
#define BROWSE_INTERVAL (60)
#define REGISTRATION_INTERVAL (10*60)
#define NMBD_INETD_TIMEOUT (120)
#define NMBD_MAX_TTL (24*60*60)
#define LPQ_LOCK_TIMEOUT (5)
#define NMBD_INTERFACES_RELOAD (120)
#define NMBD_UNEXPECTED_TIMEOUT (15)
/* the following are in milliseconds */
#define LOCK_RETRY_TIMEOUT (100)
/* do you want to dump core (carefully!) when an internal error is
encountered? Samba will be careful to make the core file only
accessible to root */
#define DUMP_CORE 1
/* shall we support browse requests via a FIFO to nmbd? */
#define ENABLE_FIFO 1
/* how long (in miliseconds) to wait for a socket connect to happen */
#define LONG_CONNECT_TIMEOUT 30000
#define SHORT_CONNECT_TIMEOUT 5000
/* the default netbios keepalive timeout */
#define DEFAULT_KEEPALIVE 300
/* the directory to sit in when idle */
/* #define IDLE_DIR "/" */
/* Timout (in seconds) to wait for an oplock break
message to return from the client. */
#define OPLOCK_BREAK_TIMEOUT 30
/* Timout (in seconds) to add to the oplock break timeout
to wait for the smbd to smbd message to return. */
#define OPLOCK_BREAK_TIMEOUT_FUDGEFACTOR 2
/* the read preciction code has been disabled until some problems with
it are worked out */
#define USE_READ_PREDICTION 0
/*
* Default passwd chat script.
*/
#define DEFAULT_PASSWD_CHAT "*new*password* %n\\n *new*password* %n\\n *changed*"
/* Minimum length of allowed password when changing UNIX password. */
#define MINPASSWDLENGTH 5
/* maximum ID number used for session control. This cannot be larger
than 62*62 for the current code */
#define MAX_SESSION_ID 3000
/* For the benifit of PAM and the 'session exec' scripts, we fake up a terminal
name. This can be in one of two forms: The first for systems not using
utmp (and therefore not constrained as to length or the need for a number
< 3000 or so) and the second for systems with this 'well behaved terminal
like name' constraint.
*/
#ifndef SESSION_TEMPLATE
/* Paramaters are 'pid' and 'vuid' */
#define SESSION_TEMPLATE "smb/%lu/%d"
#endif
#ifndef SESSION_UTMP_TEMPLATE
#define SESSION_UTMP_TEMPLATE "smb/%d"
#endif
/* the maximum age in seconds of a password. Should be a lp_ parameter */
#define MAX_PASSWORD_AGE (21*24*60*60)
/* Allocation roundup. */
#define SMB_ROUNDUP_ALLOCATION_SIZE 0x100000
/* shall we deny oplocks to clients that get timeouts? */
#define FASCIST_OPLOCK_BACKOFF 1
/* this enables the "rabbit pellet" fix for SMBwritebraw */
#define RABBIT_PELLET_FIX 1
/* Max number of jobs per print queue. */
#define PRINT_MAX_JOBID 10000
/* Max number of open RPC pipes. */
#define MAX_OPEN_PIPES 2048
/* Tuning for server auth mutex. */
#define CLI_AUTH_TIMEOUT 5000 /* In milli-seconds. */
#define NUM_CLI_AUTH_CONNECT_RETRIES 3
/* Number in seconds to wait for the mutex. This must be less than 30 seconds. */
#define SERVER_MUTEX_WAIT_TIME ( ((NUM_CLI_AUTH_CONNECT_RETRIES) * ((CLI_AUTH_TIMEOUT)/1000)) + 5)
/* Number in seconds for winbindd to wait for the mutex. Make this 2 * smbd wait time. */
#define WINBIND_SERVER_MUTEX_WAIT_TIME (( ((NUM_CLI_AUTH_CONNECT_RETRIES) * ((CLI_AUTH_TIMEOUT)/1000)) + 5)*2)
/* Max number of simultaneous winbindd socket connections. */
#define WINBINDD_MAX_SIMULTANEOUS_CLIENTS 200
#endif

14
source4/include/mangle.h Normal file
View File

@ -0,0 +1,14 @@
#ifndef _MANGLE_H_
#define _MANGLE_H_
/*
header for 8.3 name mangling interface
*/
struct mangle_fns {
BOOL (*is_mangled)(const char *s);
BOOL (*is_8_3)(const char *fname, BOOL check_case, BOOL allow_wildcards);
void (*reset)(void);
BOOL (*check_cache)(char *s);
void (*name_map)(char *OutName, BOOL need83, BOOL cache83);
};
#endif /* _MANGLE_H_ */

61
source4/include/mapping.h Normal file
View File

@ -0,0 +1,61 @@
/*
* Unix SMB/CIFS implementation.
* RPC Pipe client / server routines
* Copyright (C) Andrew Tridgell 1992-2000,
* Copyright (C) Jean François Micouleau 1998-2001.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#define PRIV_ALL_INDEX 5
#define SE_PRIV_NONE 0x0000
#define SE_PRIV_ADD_MACHINES 0x0006
#define SE_PRIV_SEC_PRIV 0x0008
#define SE_PRIV_TAKE_OWNER 0x0009
#define SE_PRIV_ADD_USERS 0xff01
#define SE_PRIV_PRINT_OPERATOR 0xff03
#define SE_PRIV_ALL 0xffff
#define ENUM_ONLY_MAPPED True
#define ENUM_ALL_MAPPED False
#define MAPPING_WITH_PRIV True
#define MAPPING_WITHOUT_PRIV False
#define PR_NONE 0x0000
#define PR_LOG_ON_LOCALLY 0x0001
#define PR_ACCESS_FROM_NETWORK 0x0002
#define PR_LOG_ON_BATCH_JOB 0x0004
#define PR_LOG_ON_SERVICE 0x0010
typedef struct _GROUP_MAP {
struct pdb_methods *methods;
gid_t gid;
DOM_SID sid;
enum SID_NAME_USE sid_name_use;
fstring nt_name;
fstring comment;
uint32 systemaccount;
PRIVILEGE_SET priv_set;
} GROUP_MAP;
typedef struct _PRIVS {
uint32 se_priv;
const char *priv;
const char *description;
} PRIVS;

24
source4/include/md5.h Normal file
View File

@ -0,0 +1,24 @@
#ifndef MD5_H
#define MD5_H
#ifndef HEADER_MD5_H
/* Try to avoid clashes with OpenSSL */
#define HEADER_MD5_H
#endif
struct MD5Context {
uint32 buf[4];
uint32 bits[2];
unsigned char in[64];
};
void MD5Init(struct MD5Context *context);
void MD5Update(struct MD5Context *context, unsigned char const *buf,
unsigned len);
void MD5Final(unsigned char digest[16], struct MD5Context *context);
/*
* This is needed to make RSAREF happy on some MS-DOS compilers.
*/
typedef struct MD5Context MD5_CTX;
#endif /* !MD5_H */

View File

@ -0,0 +1,75 @@
/*
Unix SMB/CIFS implementation.
messages.c header
Copyright (C) Andrew Tridgell 2000
Copyright (C) 2001, 2002 by Martin Pool
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _MESSAGES_H_
#define _MESSAGES_H_
/* general messages */
#define MSG_DEBUG 1
#define MSG_PING 2
#define MSG_PONG 3
#define MSG_PROFILE 4
#define MSG_REQ_DEBUGLEVEL 5
#define MSG_DEBUGLEVEL 6
#define MSG_REQ_PROFILELEVEL 7
#define MSG_PROFILELEVEL 8
#define MSG_REQ_POOL_USAGE 9
#define MSG_POOL_USAGE 10
/* If dmalloc is included, set a steady-state mark */
#define MSG_REQ_DMALLOC_MARK 11
/* If dmalloc is included, dump to the dmalloc log a description of
* what has changed since the last MARK */
#define MSG_REQ_DMALLOC_LOG_CHANGED 12
#define MSG_SHUTDOWN 13
/* Dump out the talloc useage. */
#define MSG_REQ_TALLOC_USAGE 14
#define MSG_TALLOC_USAGE 15
/* nmbd messages */
#define MSG_FORCE_ELECTION 1001
#define MSG_WINS_NEW_ENTRY 1002
/* printing messages */
/* #define MSG_PRINTER_NOTIFY 2001*/ /* Obsolete */
#define MSG_PRINTER_DRVUPGRADE 2002
#define MSG_PRINTER_NOTIFY2 2003
#define MSG_PRINTERDATA_INIT_RESET 2004
/* smbd messages */
#define MSG_SMB_CONF_UPDATED 3001
#define MSG_SMB_FORCE_TDIS 3002
#define MSG_SMB_SAM_SYNC 3003
#define MSG_SMB_SAM_REPL 3004
#define MSG_SMB_UNLOCK 3005
/* Flags to classify messages - used in message_send_all() */
/* Sender will filter by flag. */
#define FLAG_MSG_GENERAL 0x0001
#define FLAG_MSG_SMBD 0x0002
#define FLAG_MSG_NMBD 0x0004
#define FLAG_MSG_PRINTING 0x0008
#endif

77
source4/include/msdfs.h Normal file
View File

@ -0,0 +1,77 @@
/*
Unix SMB/Netbios implementation.
Version 3.0
MSDfs services for Samba
Copyright (C) Shirish Kalele 2000
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _MSDFS_H
#define _MSDFS_H
#define REFERRAL_TTL 600
/* Flags used in trans2 Get Referral reply */
#define DFSREF_REFERRAL_SERVER 0x1
#define DFSREF_STORAGE_SERVER 0x2
/* Referral sizes */
#define VERSION2_REFERRAL_SIZE 0x16
#define VERSION3_REFERRAL_SIZE 0x22
#define REFERRAL_HEADER_SIZE 0x08
/* Maximum number of referrals for each Dfs volume */
#define MAX_REFERRAL_COUNT 256
struct referral
{
pstring alternate_path; /* contains the path referred */
uint32 proximity;
uint32 ttl; /* how long should client cache referral */
};
struct junction_map
{
pstring service_name;
pstring volume_name;
int referral_count;
struct referral* referral_list;
};
struct dfs_path
{
pstring hostname;
pstring servicename;
pstring reqpath;
};
#define RESOLVE_DFSPATH(name, conn, inbuf, outbuf) \
{ if ((SVAL(inbuf,smb_flg2) & FLAGS2_DFS_PATHNAMES) && \
lp_host_msdfs() && lp_msdfs_root(SNUM(conn)) && \
dfs_redirect(name,conn,False)) \
return ERROR_BOTH(NT_STATUS_PATH_NOT_COVERED, \
ERRSRV, ERRbadpath);; }
#define RESOLVE_FINDFIRST_DFSPATH(name, conn, inbuf, outbuf) \
{ if ( (SVAL(inbuf,smb_flg2) & FLAGS2_DFS_PATHNAMES) || \
((get_remote_arch() == RA_WIN95) && lp_msdfs_root(SNUM(conn))) ) \
if (lp_host_msdfs() && dfs_redirect(name,conn,True)) \
return ERROR_BOTH(NT_STATUS_PATH_NOT_COVERED, \
ERRSRV, ERRbadpath);; }
#endif /* _MSDFS_H */

79
source4/include/mutex.h Normal file
View File

@ -0,0 +1,79 @@
#ifndef _MUTEX_H_
#define _MUTEX_H_
/*
Unix SMB/CIFS implementation.
Samba mutex functions
Copyright (C) Andrew Tridgell 2003
Copyright (C) James J Myers 2003
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* To add a new mutex, add it to enum mutex_id
*/
enum mutex_id { MUTEX_SMBD, /* global smbd lock */
MUTEX_TALLOC, /* global talloc.c lock */
MUTEX_DEBUG, /* global debug.c lock */
MUTEX_TANK, /* vfs_tank lock */
MUTEX_MAX /* this MUST be kept last */
};
/* To add a new read/write lock, add it to enum rwlock_id
*/
enum rwlock_id { RWLOCK_SMBD, /* global smbd lock */
RWLOCK_MAX /* this MUST be kept last */
};
#define MUTEX_LOCK_BY_ID(mutex_index) mutex_lock_by_id(mutex_index, #mutex_index)
#define MUTEX_UNLOCK_BY_ID(mutex_index) mutex_unlock_by_id(mutex_index, #mutex_index)
#define MUTEX_INIT(mutex, name) mutex_init(mutex, #name)
#define MUTEX_DESTROY(mutex, name) mutex_destroy(mutex, #name)
#define MUTEX_LOCK(mutex, name) mutex_lock(mutex, #name)
#define MUTEX_UNLOCK(mutex, name) mutex_unlock(mutex, #name)
#define RWLOCK_INIT(rwlock, name) rwlock_init(rwlock, #name)
#define RWLOCK_DESTROY(rwlock, name) rwlock_destroy(rwlock, #name)
#define RWLOCK_LOCK_WRITE(rwlock, name) rwlock_lock_write(rwlock, #name)
#define RWLOCK_LOCK_READ(rwlock, name) rwlock_lock_read(rwlock, #name)
#define RWLOCK_UNLOCK(rwlock, name) rwlock_unlock(rwlock, #name)
/* this null typedef ensures we get the types right and avoids the
pitfalls of void* */
typedef struct {
void *mutex;
} mutex_t;
typedef struct {
void *rwlock;
} rwlock_t;
/* the mutex model operations structure - contains function pointers to
the model-specific implementations of each operation */
struct mutex_ops {
int (*mutex_init)(mutex_t *mutex, const char *name);
int (*mutex_lock)(mutex_t *mutex, const char *name);
int (*mutex_unlock)(mutex_t *mutex, const char *name);
int (*mutex_destroy)(mutex_t *mutex, const char *name);
int (*rwlock_init)(rwlock_t *rwlock, const char *name);
int (*rwlock_lock_write)(rwlock_t *rwlock, const char *name);
int (*rwlock_lock_read)(rwlock_t *rwlock, const char *name);
int (*rwlock_unlock)(rwlock_t *rwlock, const char *name);
int (*rwlock_destroy)(rwlock_t *rwlock, const char *name);
};
#endif /* ndef _MUTEX_H_ */

644
source4/include/nameserv.h Normal file
View File

@ -0,0 +1,644 @@
#ifndef _NAMESERV_H_
#define _NAMESERV_H_
/*
Unix SMB/CIFS implementation.
NBT netbios header - version 2
Copyright (C) Andrew Tridgell 1994-1998
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#define INFO_VERSION "INFO/version"
#define INFO_COUNT "INFO/num_entries"
#define INFO_ID_HIGH "INFO/id_high"
#define INFO_ID_LOW "INFO/id_low"
#define ENTRY_PREFIX "ENTRY/"
#define PERMANENT_TTL 0
/* NTAS uses 2, NT uses 1, WfWg uses 0 */
#define MAINTAIN_LIST 2
#define ELECTION_VERSION 1
#define MAX_DGRAM_SIZE (576) /* tcp/ip datagram limit is 576 bytes */
#define MIN_DGRAM_SIZE 12
/*********************************************************
Types of reply packet.
**********************************************************/
enum netbios_reply_type_code { NMB_QUERY, NMB_STATUS, NMB_REG, NMB_REG_REFRESH,
NMB_REL, NMB_WAIT_ACK, NMB_MULTIHOMED_REG,
WINS_REG, WINS_QUERY };
/* From rfc1002, 4.2.1.2 */
/* Question types. */
#define QUESTION_TYPE_NB_QUERY 0x20
#define QUESTION_TYPE_NB_STATUS 0x21
/* Question class */
#define QUESTION_CLASS_IN 0x1
/* Opcode definitions */
#define NMB_NAME_QUERY_OPCODE 0x0
#define NMB_NAME_REG_OPCODE 0x05 /* see rfc1002.txt 4.2.2,3,5,6,7,8 */
#define NMB_NAME_RELEASE_OPCODE 0x06 /* see rfc1002.txt 4.2.9,10,11 */
#define NMB_WACK_OPCODE 0x07 /* see rfc1002.txt 4.2.16 */
/* Ambiguity in rfc1002 about which of these is correct. */
/* WinNT uses 8 by default but can be made to use 9. */
#define NMB_NAME_REFRESH_OPCODE_8 0x08 /* see rfc1002.txt 4.2.4 */
#define NMB_NAME_REFRESH_OPCODE_9 0x09 /* see rfc1002.txt 4.2.4 */
#define NMB_NAME_MULTIHOMED_REG_OPCODE 0x0F /* Invented by Microsoft. */
/* XXXX what about all the other types?? 0x1, 0x2, 0x3, 0x4, 0x8? */
/* Resource record types. rfc1002 4.2.1.3 */
#define RR_TYPE_A 0x1
#define RR_TYPE_NS 0x2
#define RR_TYPE_NULL 0xA
#define RR_TYPE_NB 0x20
#define RR_TYPE_NBSTAT 0x21
/* Resource record class. */
#define RR_CLASS_IN 0x1
/* NetBIOS flags */
#define NB_GROUP 0x80
#define NB_PERM 0x02
#define NB_ACTIVE 0x04
#define NB_CONFL 0x08
#define NB_DEREG 0x10
#define NB_BFLAG 0x00 /* Broadcast node type. */
#define NB_PFLAG 0x20 /* Point-to-point node type. */
#define NB_MFLAG 0x40 /* Mixed bcast & p-p node type. */
#define NB_HFLAG 0x60 /* Microsoft 'hybrid' node type. */
#define NB_NODETYPEMASK 0x60
/* Mask applied to outgoing NetBIOS flags. */
#define NB_FLGMSK 0xE0
/* The wins flags. Looks like the nbflags ! */
#define WINS_UNIQUE 0x00 /* Unique record */
#define WINS_NGROUP 0x01 /* Normal Group eg: 1B */
#define WINS_SGROUP 0x02 /* Special Group eg: 1C */
#define WINS_MHOMED 0x03 /* MultiHomed */
#define WINS_ACTIVE 0x00 /* active record */
#define WINS_RELEASED 0x04 /* released record */
#define WINS_TOMBSTONED 0x08 /* tombstoned record */
#define WINS_DELETED 0x0C /* deleted record */
#define WINS_STATE_MASK 0x0C
#define WINS_LOCAL 0x00 /* local record */
#define WINS_REMOTE 0x10 /* remote record */
#define WINS_BNODE 0x00 /* Broadcast node */
#define WINS_PNODE 0x20 /* PtP node */
#define WINS_MNODE 0x40 /* Mixed node */
#define WINS_HNODE 0x60 /* Hybrid node */
#define WINS_NONSTATIC 0x00 /* dynamic record */
#define WINS_STATIC 0x80 /* static record */
#define WINS_STATE_ACTIVE(p) (((p)->data.wins_flags & WINS_STATE_MASK) == WINS_ACTIVE)
/* NetBIOS flag identifier. */
#define NAME_GROUP(p) ((p)->data.nb_flags & NB_GROUP)
#define NAME_BFLAG(p) (((p)->data.nb_flags & NB_NODETYPEMASK) == NB_BFLAG)
#define NAME_PFLAG(p) (((p)->data.nb_flags & NB_NODETYPEMASK) == NB_PFLAG)
#define NAME_MFLAG(p) (((p)->data.nb_flags & NB_NODETYPEMASK) == NB_MFLAG)
#define NAME_HFLAG(p) (((p)->data.nb_flags & NB_NODETYPEMASK) == NB_HFLAG)
/* Samba name state for a name in a namelist. */
#define NAME_IS_ACTIVE(p) ((p)->data.nb_flags & NB_ACTIVE)
#define NAME_IN_CONFLICT(p) ((p)->data.nb_flags & NB_CONFL)
#define NAME_IS_DEREGISTERING(p) ((p)->data.nb_flags & NB_DEREG)
/* Error codes for NetBIOS requests. */
#define FMT_ERR 0x1 /* Packet format error. */
#define SRV_ERR 0x2 /* Internal server error. */
#define NAM_ERR 0x3 /* Name does not exist. */
#define IMP_ERR 0x4 /* Request not implemented. */
#define RFS_ERR 0x5 /* Request refused. */
#define ACT_ERR 0x6 /* Active error - name owned by another host. */
#define CFT_ERR 0x7 /* Name in conflict error. */
#define REFRESH_TIME (15*60)
#define NAME_POLL_REFRESH_TIME (5*60)
#define NAME_POLL_INTERVAL 15
/* Workgroup state identifiers. */
#define AM_POTENTIAL_MASTER_BROWSER(work) ((work)->mst_state == MST_POTENTIAL)
#define AM_LOCAL_MASTER_BROWSER(work) ((work)->mst_state == MST_BROWSER)
#define AM_DOMAIN_MASTER_BROWSER(work) ((work)->dom_state == DOMAIN_MST)
#define AM_DOMAIN_MEMBER(work) ((work)->log_state == LOGON_SRV)
/* Microsoft browser NetBIOS name. */
#define MSBROWSE "\001\002__MSBROWSE__\002"
/* Mail slots. */
#define BROWSE_MAILSLOT "\\MAILSLOT\\BROWSE"
#define NET_LOGON_MAILSLOT "\\MAILSLOT\\NET\\NETLOGON"
#define NT_LOGON_MAILSLOT "\\MAILSLOT\\NET\\NTLOGON"
#define LANMAN_MAILSLOT "\\MAILSLOT\\LANMAN"
/* Samba definitions for find_name_on_subnet(). */
#define FIND_ANY_NAME 0
#define FIND_SELF_NAME 1
/*
* The different name types that can be in namelists.
*
* SELF_NAME should only be on the broadcast and unicast subnets.
* LMHOSTS_NAME should only be in the remote_broadcast_subnet.
* REGISTER_NAME, DNS_NAME, DNSFAIL_NAME should only be in the wins_server_subnet.
* WINS_PROXY_NAME should only be on the broadcast subnets.
* PERMANENT_NAME can be on all subnets except remote_broadcast_subnet.
*
*/
enum name_source {LMHOSTS_NAME, REGISTER_NAME, SELF_NAME, DNS_NAME,
DNSFAIL_NAME, PERMANENT_NAME, WINS_PROXY_NAME};
enum node_type {B_NODE=0, P_NODE=1, M_NODE=2, NBDD_NODE=3};
enum packet_type {NMB_PACKET, DGRAM_PACKET};
enum master_state
{
MST_NONE,
MST_POTENTIAL,
MST_BACKUP,
MST_MSB,
MST_BROWSER,
MST_UNBECOMING_MASTER
};
enum domain_state
{
DOMAIN_NONE,
DOMAIN_WAIT,
DOMAIN_MST
};
enum logon_state
{
LOGON_NONE,
LOGON_WAIT,
LOGON_SRV
};
struct subnet_record;
struct nmb_data
{
uint16 nb_flags; /* Netbios flags. */
int num_ips; /* Number of ip entries. */
struct in_addr *ip; /* The ip list for this name. */
enum name_source source; /* Where the name came from. */
time_t death_time; /* The time the record must be removed (do not remove if 0). */
time_t refresh_time; /* The time the record should be refreshed. */
SMB_BIG_UINT id; /* unique id */
struct in_addr wins_ip; /* the adress of the wins server this record comes from */
int wins_flags; /* similar to the netbios flags but different ! */
};
/* This structure represents an entry in a local netbios name list. */
struct name_record
{
#if 0
ubi_trNode node[1];
#endif
struct subnet_record *subnet;
struct nmb_name name; /* The netbios name. */
struct nmb_data data; /* The netbios data. */
};
/* Browser cache for synchronising browse lists. */
struct browse_cache_record
{
#if 0
ubi_dlNode node[1];
#endif
pstring lmb_name;
pstring work_group;
struct in_addr ip;
time_t sync_time;
time_t death_time; /* The time the record must be removed. */
};
/* This is used to hold the list of servers in my domain, and is
contained within lists of domains. */
struct server_record
{
struct server_record *next;
struct server_record *prev;
struct subnet_record *subnet;
struct server_info_struct serv;
time_t death_time;
};
/* A workgroup structure. It contains a list of servers. */
struct work_record
{
struct work_record *next;
struct work_record *prev;
struct subnet_record *subnet;
struct server_record *serverlist;
/* Stage of development from non-local-master up to local-master browser. */
enum master_state mst_state;
/* Stage of development from non-domain-master to domain-master browser. */
enum domain_state dom_state;
/* Stage of development from non-logon-server to logon server. */
enum logon_state log_state;
/* Work group info. */
fstring work_group;
int token; /* Used when communicating with backup browsers. */
fstring local_master_browser_name; /* Current local master browser. */
/* Announce info. */
time_t lastannounce_time;
int announce_interval;
BOOL needannounce;
/* Timeout time for this workgroup. 0 means permanent. */
time_t death_time;
/* Election info */
BOOL RunningElection;
BOOL needelection;
int ElectionCount;
uint32 ElectionCriterion;
/* Domain master browser info. Used for efficient syncs. */
struct nmb_name dmb_name;
struct in_addr dmb_addr;
};
/* typedefs needed to define copy & free functions for userdata. */
struct userdata_struct;
typedef struct userdata_struct * (*userdata_copy_fn)(struct userdata_struct *);
typedef void (*userdata_free_fn)(struct userdata_struct *);
/* Structure to define any userdata passed around. */
struct userdata_struct {
userdata_copy_fn copy_fn;
userdata_free_fn free_fn;
unsigned int userdata_len;
char data[16]; /* 16 is to ensure alignment/padding on all systems */
};
struct response_record;
struct packet_struct;
struct res_rec;
/* typedef to define the function called when this response packet comes in. */
typedef void (*response_function)(struct subnet_record *, struct response_record *,
struct packet_struct *);
/* typedef to define the function called when this response record times out. */
typedef void (*timeout_response_function)(struct subnet_record *,
struct response_record *);
/* typedef to define the function called when the request that caused this
response record to be created is successful. */
typedef void (*success_function)(struct subnet_record *, struct userdata_struct *, ...);
/* typedef to define the function called when the request that caused this
response record to be created is unsuccessful. */
typedef void (*fail_function)(struct subnet_record *, struct response_record *, ...);
/* List of typedefs for success and fail functions of the different query
types. Used to catch any compile time prototype errors. */
typedef void (*register_name_success_function)( struct subnet_record *,
struct userdata_struct *,
struct nmb_name *,
uint16,
int,
struct in_addr);
typedef void (*register_name_fail_function)( struct subnet_record *,
struct response_record *,
struct nmb_name *);
typedef void (*release_name_success_function)( struct subnet_record *,
struct userdata_struct *,
struct nmb_name *,
struct in_addr);
typedef void (*release_name_fail_function)( struct subnet_record *,
struct response_record *,
struct nmb_name *);
typedef void (*refresh_name_success_function)( struct subnet_record *,
struct userdata_struct *,
struct nmb_name *,
uint16,
int,
struct in_addr);
typedef void (*refresh_name_fail_function)( struct subnet_record *,
struct response_record *,
struct nmb_name *);
typedef void (*query_name_success_function)( struct subnet_record *,
struct userdata_struct *,
struct nmb_name *,
struct in_addr,
struct res_rec *answers);
typedef void (*query_name_fail_function)( struct subnet_record *,
struct response_record *,
struct nmb_name *,
int);
typedef void (*node_status_success_function)( struct subnet_record *,
struct userdata_struct *,
struct res_rec *,
struct in_addr);
typedef void (*node_status_fail_function)( struct subnet_record *,
struct response_record *);
/* Initiated name queries are recorded in this list to track any responses. */
struct response_record
{
struct response_record *next;
struct response_record *prev;
uint16 response_id;
/* Callbacks for packets received or not. */
response_function resp_fn;
timeout_response_function timeout_fn;
/* Callbacks for the request succeeding or not. */
success_function success_fn;
fail_function fail_fn;
struct packet_struct *packet;
struct userdata_struct *userdata;
int num_msgs;
time_t repeat_time;
time_t repeat_interval;
int repeat_count;
/* Recursion protection. */
BOOL in_expiration_processing;
};
/* A subnet structure. It contains a list of workgroups and netbios names. */
/*
B nodes will have their own, totally separate subnet record, with their
own netbios name set. These do NOT interact with other subnet records'
netbios names.
*/
enum subnet_type {
NORMAL_SUBNET = 0, /* Subnet listed in interfaces list. */
UNICAST_SUBNET = 1, /* Subnet for unicast packets. */
REMOTE_BROADCAST_SUBNET = 2, /* Subnet for remote broadcasts. */
WINS_SERVER_SUBNET = 3 /* Only created if we are a WINS server. */
};
struct subnet_record
{
struct subnet_record *next;
struct subnet_record *prev;
char *subnet_name; /* For Debug identification. */
enum subnet_type type; /* To catagorize the subnet. */
struct work_record *workgrouplist; /* List of workgroups. */
#if 0
ubi_trRoot namelist[1]; /* List of netbios names. */
#endif
struct response_record *responselist; /* List of responses expected. */
BOOL namelist_changed;
BOOL work_changed;
struct in_addr bcast_ip;
struct in_addr mask_ip;
struct in_addr myip;
int nmb_sock; /* socket to listen for unicast 137. */
int dgram_sock; /* socket to listen for unicast 138. */
};
/* A resource record. */
struct res_rec {
struct nmb_name rr_name;
int rr_type;
int rr_class;
int ttl;
int rdlength;
char rdata[MAX_DGRAM_SIZE];
};
/* Define these so we can pass info back to caller of name_query */
#define NM_FLAGS_RS 0x80 /* Response. Cheat */
#define NM_FLAGS_AA 0x40 /* Authoritative */
#define NM_FLAGS_TC 0x20 /* Truncated */
#define NM_FLAGS_RD 0x10 /* Recursion Desired */
#define NM_FLAGS_RA 0x08 /* Recursion Available */
#define NM_FLAGS_B 0x01 /* Broadcast */
/* An nmb packet. */
struct nmb_packet
{
struct {
int name_trn_id;
int opcode;
BOOL response;
struct {
BOOL bcast;
BOOL recursion_available;
BOOL recursion_desired;
BOOL trunc;
BOOL authoritative;
} nm_flags;
int rcode;
int qdcount;
int ancount;
int nscount;
int arcount;
} header;
struct {
struct nmb_name question_name;
int question_type;
int question_class;
} question;
struct res_rec *answers;
struct res_rec *nsrecs;
struct res_rec *additional;
};
/* msg_type field options - from rfc1002. */
#define DGRAM_UNIQUE 0x10
#define DGRAM_GROUP 0x11
#define DGRAM_BROADCAST 0x12
#define DGRAM_ERROR 0x13
#define DGRAM_QUERY_REQUEST 0x14
#define DGRAM_POSITIVE_QUERY_RESPONSE 0x15
#define DGRAM_NEGATIVE_QUERT_RESPONSE 0x16
/* A datagram - this normally contains SMB data in the data[] array. */
struct dgram_packet {
struct {
int msg_type;
struct {
enum node_type node_type;
BOOL first;
BOOL more;
} flags;
int dgm_id;
struct in_addr source_ip;
int source_port;
int dgm_length;
int packet_offset;
} header;
struct nmb_name source_name;
struct nmb_name dest_name;
int datasize;
char data[MAX_DGRAM_SIZE];
};
/* Define a structure used to queue packets. This will be a linked
list of nmb packets. */
struct packet_struct
{
struct packet_struct *next;
struct packet_struct *prev;
BOOL locked;
struct in_addr ip;
int port;
int fd;
time_t timestamp;
enum packet_type packet_type;
union {
struct nmb_packet nmb;
struct dgram_packet dgram;
} packet;
};
/* NETLOGON opcodes */
#define QUERYFORPDC 7 /* Query for PDC. */
#define SAM_UAS_CHANGE 10 /* Announce change to UAS or SAM. */
#define QUERYFORPDC_R 12 /* Response to Query for PDC. */
#define SAMLOGON 18
#define SAMLOGON_R 19
#define SAMLOGON_UNK_R 21
#define SAMLOGON_AD_UNK_R 23
#define SAMLOGON_AD_R 25
/* Ids for netbios packet types. */
#define ANN_HostAnnouncement 1
#define ANN_AnnouncementRequest 2
#define ANN_Election 8
#define ANN_GetBackupListReq 9
#define ANN_GetBackupListResp 10
#define ANN_BecomeBackup 11
#define ANN_DomainAnnouncement 12
#define ANN_MasterAnnouncement 13
#define ANN_ResetBrowserState 14
#define ANN_LocalMasterAnnouncement 15
/* Broadcast packet announcement intervals, in minutes. */
/* Attempt to add domain logon and domain master names. */
#define CHECK_TIME_ADD_DOM_NAMES 5
/* Search for master browsers of workgroups samba knows about,
except default. */
#define CHECK_TIME_MST_BROWSE 5
/* Request backup browser announcements from other servers. */
#define CHECK_TIME_ANNOUNCE_BACKUP 15
/* Request host announcements from other servers: min and max of interval. */
#define CHECK_TIME_MIN_HOST_ANNCE 3
#define CHECK_TIME_MAX_HOST_ANNCE 12
/* Announce as master to WINS server and any Primary Domain Controllers. */
#define CHECK_TIME_MST_ANNOUNCE 15
/* Time between syncs from domain master browser to local master browsers. */
#define CHECK_TIME_DMB_TO_LMB_SYNC 15
/* Do all remote announcements this often. */
#define REMOTE_ANNOUNCE_INTERVAL 180
/* what is the maximum period between name refreshes. Note that this only
affects non-permanent self names (in seconds) */
#define MAX_REFRESH_TIME (60*20)
/* The Extinction interval: 4 days, time a node will stay in released state */
#define EXTINCTION_INTERVAL (4*24*60*60)
/* The Extinction time-out: 1 day, time a node will stay in deleted state */
#define EXTINCTION_TIMEOUT (24*60*60)
/* Macro's to enumerate subnets either with or without
the UNICAST subnet. */
extern struct subnet_record *subnetlist;
extern struct subnet_record *unicast_subnet;
extern struct subnet_record *wins_server_subnet;
extern struct subnet_record *remote_broadcast_subnet;
#define FIRST_SUBNET subnetlist
#define NEXT_SUBNET_EXCLUDING_UNICAST(x) ((x)->next)
#define NEXT_SUBNET_INCLUDING_UNICAST(x) (get_next_subnet_maybe_unicast((x)))
/* wins replication record used between nmbd and wrepld */
typedef struct _WINS_RECORD {
char name[17];
char type;
int nb_flags;
int wins_flags;
SMB_BIG_UINT id;
int num_ips;
struct in_addr ip[25];
struct in_addr wins_ip;
} WINS_RECORD;
/* To be removed. */
enum state_type { TEST };
#endif /* _NAMESERV_H_ */

View File

@ -0,0 +1,482 @@
/*
Unix SMB/Netbios implementation.
Version 1.9.
SMB parameters and setup
Copyright (C) Andrew Tridgell 1992-2000,
Copyright (C) Jean Francois Micouleau 1998-2000.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef NT_PRINTING_H_
#define NT_PRINTING_H_
#define ORIENTATION 0x00000001L
#define PAPERSIZE 0x00000002L
#define PAPERLENGTH 0x00000004L
#define PAPERWIDTH 0x00000008L
#define SCALE 0x00000010L
#define COPIES 0x00000100L
#define DEFAULTSOURCE 0x00000200L
#define PRINTQUALITY 0x00000400L
#define COLOR 0x00000800L
#define DUPLEX 0x00001000L
#define YRESOLUTION 0x00002000L
#define TTOPTION 0x00004000L
#define COLLATE 0x00008000L
#define FORMNAME 0x00010000L
#define LOGPIXELS 0x00020000L
#define BITSPERPEL 0x00040000L
#define PELSWIDTH 0x00080000L
#define PELSHEIGHT 0x00100000L
#define DISPLAYFLAGS 0x00200000L
#define DISPLAYFREQUENCY 0x00400000L
#define PANNINGWIDTH 0x00800000L
#define PANNINGHEIGHT 0x01000000L
#define ORIENT_PORTRAIT 1
#define ORIENT_LANDSCAPE 2
#define PAPER_FIRST PAPER_LETTER
#define PAPER_LETTER 1 /* Letter 8 1/2 x 11 in */
#define PAPER_LETTERSMALL 2 /* Letter Small 8 1/2 x 11 in */
#define PAPER_TABLOID 3 /* Tabloid 11 x 17 in */
#define PAPER_LEDGER 4 /* Ledger 17 x 11 in */
#define PAPER_LEGAL 5 /* Legal 8 1/2 x 14 in */
#define PAPER_STATEMENT 6 /* Statement 5 1/2 x 8 1/2 in */
#define PAPER_EXECUTIVE 7 /* Executive 7 1/4 x 10 1/2 in */
#define PAPER_A3 8 /* A3 297 x 420 mm */
#define PAPER_A4 9 /* A4 210 x 297 mm */
#define PAPER_A4SMALL 10 /* A4 Small 210 x 297 mm */
#define PAPER_A5 11 /* A5 148 x 210 mm */
#define PAPER_B4 12 /* B4 (JIS) 250 x 354 */
#define PAPER_B5 13 /* B5 (JIS) 182 x 257 mm */
#define PAPER_FOLIO 14 /* Folio 8 1/2 x 13 in */
#define PAPER_QUARTO 15 /* Quarto 215 x 275 mm */
#define PAPER_10X14 16 /* 10x14 in */
#define PAPER_11X17 17 /* 11x17 in */
#define PAPER_NOTE 18 /* Note 8 1/2 x 11 in */
#define PAPER_ENV_9 19 /* Envelope #9 3 7/8 x 8 7/8 */
#define PAPER_ENV_10 20 /* Envelope #10 4 1/8 x 9 1/2 */
#define PAPER_ENV_11 21 /* Envelope #11 4 1/2 x 10 3/8 */
#define PAPER_ENV_12 22 /* Envelope #12 4 \276 x 11 */
#define PAPER_ENV_14 23 /* Envelope #14 5 x 11 1/2 */
#define PAPER_CSHEET 24 /* C size sheet */
#define PAPER_DSHEET 25 /* D size sheet */
#define PAPER_ESHEET 26 /* E size sheet */
#define PAPER_ENV_DL 27 /* Envelope DL 110 x 220mm */
#define PAPER_ENV_C5 28 /* Envelope C5 162 x 229 mm */
#define PAPER_ENV_C3 29 /* Envelope C3 324 x 458 mm */
#define PAPER_ENV_C4 30 /* Envelope C4 229 x 324 mm */
#define PAPER_ENV_C6 31 /* Envelope C6 114 x 162 mm */
#define PAPER_ENV_C65 32 /* Envelope C65 114 x 229 mm */
#define PAPER_ENV_B4 33 /* Envelope B4 250 x 353 mm */
#define PAPER_ENV_B5 34 /* Envelope B5 176 x 250 mm */
#define PAPER_ENV_B6 35 /* Envelope B6 176 x 125 mm */
#define PAPER_ENV_ITALY 36 /* Envelope 110 x 230 mm */
#define PAPER_ENV_MONARCH 37 /* Envelope Monarch 3.875 x 7.5 in */
#define PAPER_ENV_PERSONAL 38 /* 6 3/4 Envelope 3 5/8 x 6 1/2 in */
#define PAPER_FANFOLD_US 39 /* US Std Fanfold 14 7/8 x 11 in */
#define PAPER_FANFOLD_STD_GERMAN 40 /* German Std Fanfold 8 1/2 x 12 in */
#define PAPER_FANFOLD_LGL_GERMAN 41 /* German Legal Fanfold 8 1/2 x 13 in */
#define PAPER_LAST PAPER_FANFOLD_LGL_GERMAN
#define PAPER_USER 256
#define BIN_FIRST BIN_UPPER
#define BIN_UPPER 1
#define BIN_ONLYONE 1
#define BIN_LOWER 2
#define BIN_MIDDLE 3
#define BIN_MANUAL 4
#define BIN_ENVELOPE 5
#define BIN_ENVMANUAL 6
#define BIN_AUTO 7
#define BIN_TRACTOR 8
#define BIN_SMALLFMT 9
#define BIN_LARGEFMT 10
#define BIN_LARGECAPACITY 11
#define BIN_CASSETTE 14
#define BIN_FORMSOURCE 15
#define BIN_LAST BIN_FORMSOURCE
#define BIN_USER 256 /* device specific bins start here */
#define RES_DRAFT (-1)
#define RES_LOW (-2)
#define RES_MEDIUM (-3)
#define RES_HIGH (-4)
#define COLOR_MONOCHROME 1
#define COLOR_COLOR 2
#define DUP_SIMPLEX 1
#define DUP_VERTICAL 2
#define DUP_HORIZONTAL 3
#define TT_BITMAP 1 /* print TT fonts as graphics */
#define TT_DOWNLOAD 2 /* download TT fonts as soft fonts */
#define TT_SUBDEV 3 /* substitute device fonts for TT fonts */
#define COLLATE_FALSE 0
#define COLLATE_TRUE 1
typedef struct nt_printer_driver_info_level_3
{
uint32 cversion;
fstring name;
fstring environment;
fstring driverpath;
fstring datafile;
fstring configfile;
fstring helpfile;
fstring monitorname;
fstring defaultdatatype;
fstring *dependentfiles;
} NT_PRINTER_DRIVER_INFO_LEVEL_3;
/* SPOOL_PRINTER_DRIVER_INFO_LEVEL_6 structure */
typedef struct {
uint32 version;
fstring name;
fstring environment;
fstring driverpath;
fstring datafile;
fstring configfile;
fstring helpfile;
fstring monitorname;
fstring defaultdatatype;
fstring mfgname;
fstring oemurl;
fstring hardwareid;
fstring provider;
fstring *dependentfiles;
fstring *previousnames;
} NT_PRINTER_DRIVER_INFO_LEVEL_6;
typedef struct nt_printer_driver_info_level
{
NT_PRINTER_DRIVER_INFO_LEVEL_3 *info_3;
NT_PRINTER_DRIVER_INFO_LEVEL_6 *info_6;
} NT_PRINTER_DRIVER_INFO_LEVEL;
/* predefined registry key names for printer data */
#define SPOOL_PRINTERDATA_KEY "PrinterDriverData"
#define SPOOL_DSSPOOLER_KEY "DsSpooler"
#define SPOOL_DSDRIVER_KEY "DsDriver"
#define SPOOL_DSUSER_KEY "DsUser"
#define SPOOL_PNPDATA_KEY "PnPData"
#define SPOOL_OID_KEY "OID"
/* predefined value names for printer data */
#define SPOOL_REG_ASSETNUMBER "assetNumber"
#define SPOOL_REG_BYTESPERMINUTE "bytesPerMinute"
#define SPOOL_REG_DEFAULTPRIORITY "defaultPriority"
#define SPOOL_REG_DESCRIPTION "description"
#define SPOOL_REG_DRIVERNAME "driverName"
#define SPOOL_REG_DRIVERVERSION "driverVersion"
#define SPOOL_REG_FLAGS "flags"
#define SPOOL_REG_LOCATION "location"
#define SPOOL_REG_OPERATINGSYSTEM "operatingSystem"
#define SPOOL_REG_OPERATINGSYSTEMHOTFIX "operatingSystemHotfix"
#define SPOOL_REG_OPERATINGSYSTEMSERVICEPACK "operatingSystemServicePack"
#define SPOOL_REG_OPERATINGSYSTEMVERSION "operatingSystemVersion"
#define SPOOL_REG_PORTNAME "portName"
#define SPOOL_REG_PRINTATTRIBUTES "printAttributes"
#define SPOOL_REG_PRINTBINNAMES "printBinNames"
#define SPOOL_REG_PRINTCOLLATE "printCollate"
#define SPOOL_REG_PRINTCOLOR "printColor"
#define SPOOL_REG_PRINTDUPLEXSUPPORTED "printDuplexSupported"
#define SPOOL_REG_PRINTENDTIME "printEndTime"
#define SPOOL_REG_PRINTERNAME "printerName"
#define SPOOL_REG_PRINTFORMNAME "printFormName"
#define SPOOL_REG_PRINTKEEPPRINTEDJOBS "printKeepPrintedJobs"
#define SPOOL_REG_PRINTLANGUAGE "printLanguage"
#define SPOOL_REG_PRINTMACADDRESS "printMACAddress"
#define SPOOL_REG_PRINTMAXCOPIES "printMaxCopies"
#define SPOOL_REG_PRINTMAXRESOLUTIONSUPPORTED "printMaxResolutionSupported"
#define SPOOL_REG_PRINTMAXXEXTENT "printMaxXExtent"
#define SPOOL_REG_PRINTMAXYEXTENT "printMaxYExtent"
#define SPOOL_REG_PRINTMEDIAREADY "printMediaReady"
#define SPOOL_REG_PRINTMEDIASUPPORTED "printMediaSupported"
#define SPOOL_REG_PRINTMEMORY "printMemory"
#define SPOOL_REG_PRINTMINXEXTENT "printMinXExtent"
#define SPOOL_REG_PRINTMINYEXTENT "printMinYExtent"
#define SPOOL_REG_PRINTNETWORKADDRESS "printNetworkAddress"
#define SPOOL_REG_PRINTNOTIFY "printNotify"
#define SPOOL_REG_PRINTNUMBERUP "printNumberUp"
#define SPOOL_REG_PRINTORIENTATIONSSUPPORTED "printOrientationsSupported"
#define SPOOL_REG_PRINTOWNER "printOwner"
#define SPOOL_REG_PRINTPAGESPERMINUTE "printPagesPerMinute"
#define SPOOL_REG_PRINTRATE "printRate"
#define SPOOL_REG_PRINTRATEUNIT "printRateUnit"
#define SPOOL_REG_PRINTSEPARATORFILE "printSeparatorFile"
#define SPOOL_REG_PRINTSHARENAME "printShareName"
#define SPOOL_REG_PRINTSPOOLING "printSpooling"
#define SPOOL_REGVAL_PRINTWHILESPOOLING "PrintWhileSpooling"
#define SPOOL_REGVAL_PRINTAFTERSPOOLED "PrintAfterSpooled"
#define SPOOL_REGVAL_PRINTDIRECT "PrintDirect"
#define SPOOL_REG_PRINTSTAPLINGSUPPORTED "printStaplingSupported"
#define SPOOL_REG_PRINTSTARTTIME "printStartTime"
#define SPOOL_REG_PRINTSTATUS "printStatus"
#define SPOOL_REG_PRIORITY "priority"
#define SPOOL_REG_SERVERNAME "serverName"
#define SPOOL_REG_SHORTSERVERNAME "shortServerName"
#define SPOOL_REG_UNCNAME "uNCName"
#define SPOOL_REG_URL "url"
#define SPOOL_REG_VERSIONNUMBER "versionNumber"
/* container for a single registry key */
typedef struct {
char *name;
REGVAL_CTR values;
} NT_PRINTER_KEY;
/* container for all printer data */
typedef struct {
int num_keys;
NT_PRINTER_KEY *keys;
} NT_PRINTER_DATA;
typedef struct ntdevicemode
{
fstring devicename;
fstring formname;
uint16 specversion;
uint16 driverversion;
uint16 size;
uint16 driverextra;
uint16 orientation;
uint16 papersize;
uint16 paperlength;
uint16 paperwidth;
uint16 scale;
uint16 copies;
uint16 defaultsource;
uint16 printquality;
uint16 color;
uint16 duplex;
uint16 yresolution;
uint16 ttoption;
uint16 collate;
uint16 logpixels;
uint32 fields;
uint32 bitsperpel;
uint32 pelswidth;
uint32 pelsheight;
uint32 displayflags;
uint32 displayfrequency;
uint32 icmmethod;
uint32 icmintent;
uint32 mediatype;
uint32 dithertype;
uint32 reserved1;
uint32 reserved2;
uint32 panningwidth;
uint32 panningheight;
uint8 *private;
} NT_DEVICEMODE;
typedef struct nt_printer_info_level_2
{
uint32 attributes;
uint32 priority;
uint32 default_priority;
uint32 starttime;
uint32 untiltime;
uint32 status;
uint32 cjobs;
uint32 averageppm;
fstring servername;
fstring printername;
fstring sharename;
fstring portname;
fstring drivername;
pstring comment;
fstring location;
NT_DEVICEMODE *devmode;
fstring sepfile;
fstring printprocessor;
fstring datatype;
fstring parameters;
NT_PRINTER_DATA data;
SEC_DESC_BUF *secdesc_buf;
uint32 changeid;
uint32 c_setprinter;
uint32 setuptime;
} NT_PRINTER_INFO_LEVEL_2;
typedef struct nt_printer_info_level
{
NT_PRINTER_INFO_LEVEL_2 *info_2;
} NT_PRINTER_INFO_LEVEL;
typedef struct
{
fstring name;
uint32 flag;
uint32 width;
uint32 length;
uint32 left;
uint32 top;
uint32 right;
uint32 bottom;
} nt_forms_struct;
/*
typedef struct _form
{
uint32 flags;
uint32 name_ptr;
uint32 size_x;
uint32 size_y;
uint32 left;
uint32 top;
uint32 right;
uint32 bottom;
UNISTR2 name;
} FORM;
*/
#ifndef SAMBA_PRINTER_PORT_NAME
#define SAMBA_PRINTER_PORT_NAME "Samba Printer Port"
#endif
/* DOS header format */
#define DOS_HEADER_SIZE 64
#define DOS_HEADER_MAGIC_OFFSET 0
#define DOS_HEADER_MAGIC 0x5A4D
#define DOS_HEADER_LFANEW_OFFSET 60
/* New Executable format (Win or OS/2 1.x segmented) */
#define NE_HEADER_SIZE 64
#define NE_HEADER_SIGNATURE_OFFSET 0
#define NE_HEADER_SIGNATURE 0x454E
#define NE_HEADER_TARGET_OS_OFFSET 54
#define NE_HEADER_TARGOS_WIN 0x02
#define NE_HEADER_MINOR_VER_OFFSET 62
#define NE_HEADER_MAJOR_VER_OFFSET 63
/* Portable Executable format */
#define PE_HEADER_SIZE 248
#define PE_HEADER_SIGNATURE_OFFSET 0
#define PE_HEADER_SIGNATURE 0x00004550
#define PE_HEADER_MACHINE_OFFSET 4
#define PE_HEADER_MACHINE_I386 0x14c
#define PE_HEADER_NUMBER_OF_SECTIONS 6
#define PE_HEADER_MAJOR_OS_VER_OFFSET 64
#define PE_HEADER_MINOR_OS_VER_OFFSET 66
#define PE_HEADER_MAJOR_IMG_VER_OFFSET 68
#define PE_HEADER_MINOR_IMG_VER_OFFSET 70
#define PE_HEADER_MAJOR_SS_VER_OFFSET 72
#define PE_HEADER_MINOR_SS_VER_OFFSET 74
#define PE_HEADER_SECT_HEADER_SIZE 40
#define PE_HEADER_SECT_NAME_OFFSET 0
#define PE_HEADER_SECT_SIZE_DATA_OFFSET 16
#define PE_HEADER_SECT_PTR_DATA_OFFSET 20
/* Microsoft file version format */
#define VS_SIGNATURE "VS_VERSION_INFO"
#define VS_MAGIC_VALUE 0xfeef04bd
#define VS_MAJOR_OFFSET 8
#define VS_MINOR_OFFSET 12
#define VS_VERSION_INFO_UNICODE_SIZE (sizeof(VS_SIGNATURE)*2+4+VS_MINOR_OFFSET+4) /* not true size! */
#define VS_VERSION_INFO_SIZE (sizeof(VS_SIGNATURE)+4+VS_MINOR_OFFSET+4) /* not true size! */
#define VS_NE_BUF_SIZE 4096 /* Must be > 2*VS_VERSION_INFO_SIZE */
/* Notify spoolss clients that something has changed. The
notification data is either stored in two uint32 values or a
variable length array. */
#define SPOOLSS_NOTIFY_MSG_UNIX_JOBID 0x0001 /* Job id is unix */
typedef struct spoolss_notify_msg {
fstring printer; /* Name of printer notified */
uint32 type; /* Printer or job notify */
uint32 field; /* Notify field changed */
uint32 id; /* Job id */
uint32 len; /* Length of data, 0 for two uint32 value */
uint32 flags;
union {
uint32 value[2];
char *data;
} notify;
} SPOOLSS_NOTIFY_MSG;
typedef struct {
fstring printername;
uint32 num_msgs;
SPOOLSS_NOTIFY_MSG *msgs;
} SPOOLSS_NOTIFY_MSG_GROUP;
typedef struct {
TALLOC_CTX *ctx;
uint32 num_groups;
SPOOLSS_NOTIFY_MSG_GROUP *msg_groups;
} SPOOLSS_NOTIFY_MSG_CTR;
#define PRINTER_HANDLE_IS_PRINTER 0
#define PRINTER_HANDLE_IS_PRINTSERVER 1
/* structure to store the printer handles */
/* and a reference to what it's pointing to */
/* and the notify info asked about */
/* that's the central struct */
typedef struct _Printer{
struct _Printer *prev, *next;
BOOL document_started;
BOOL page_started;
uint32 jobid; /* jobid in printing backend */
BOOL printer_type;
TALLOC_CTX *ctx;
union {
fstring handlename;
fstring printerservername;
} dev;
uint32 type;
uint32 access_granted;
struct {
uint32 flags;
uint32 options;
fstring localmachine;
uint32 printerlocal;
SPOOL_NOTIFY_OPTION *option;
POLICY_HND client_hnd;
BOOL client_connected;
uint32 change;
/* are we in a FindNextPrinterChangeNotify() call? */
BOOL fnpcn;
} notify;
struct {
fstring machine;
fstring user;
} client;
/* devmode sent in the OpenPrinter() call */
NT_DEVICEMODE *nt_devmode;
/* cache the printer info */
NT_PRINTER_INFO_LEVEL *printer_info;
} Printer_entry;
#endif /* NT_PRINTING_H_ */

View File

@ -0,0 +1,63 @@
/*
Unix SMB/CIFS implementation.
SMB parameters and setup, plus a whole lot more.
Copyright (C) Andrew Tridgell 2001
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _NT_STATUS_H
#define _NT_STATUS_H
/* The Splint code analysis tool doesn't like immediate structures. */
#ifdef _SPLINT_ /* http://www.splint.org */
#undef HAVE_IMMEDIATE_STRUCTURES
#endif
/* the following rather strange looking definitions of NTSTATUS and WERROR
and there in order to catch common coding errors where different error types
are mixed up. This is especially important as we slowly convert Samba
from using BOOL for internal functions
*/
#if defined(HAVE_IMMEDIATE_STRUCTURES)
typedef struct {uint32 v;} NTSTATUS;
#define NT_STATUS(x) ((NTSTATUS) { x })
#define NT_STATUS_V(x) ((x).v)
#else
typedef uint32 NTSTATUS;
#define NT_STATUS(x) (x)
#define NT_STATUS_V(x) (x)
#endif
#if defined(HAVE_IMMEDIATE_STRUCTURES)
typedef struct {uint32 v;} WERROR;
#define W_ERROR(x) ((WERROR) { x })
#define W_ERROR_V(x) ((x).v)
#else
typedef uint32 WERROR;
#define W_ERROR(x) (x)
#define W_ERROR_V(x) (x)
#endif
#define NT_STATUS_IS_OK(x) (NT_STATUS_V(x) == 0)
#define NT_STATUS_IS_ERR(x) ((NT_STATUS_V(x) & 0xc0000000) == 0xc0000000)
#define NT_STATUS_EQUAL(x,y) (NT_STATUS_V(x) == NT_STATUS_V(y))
#define W_ERROR_IS_OK(x) (W_ERROR_V(x) == 0)
#define W_ERROR_EQUAL(x,y) (W_ERROR_V(x) == W_ERROR_V(y))
#endif

379
source4/include/ntdomain.h Normal file
View File

@ -0,0 +1,379 @@
/*
Unix SMB/CIFS implementation.
SMB parameters and setup
Copyright (C) Andrew Tridgell 1992-1997
Copyright (C) Luke Kenneth Casson Leighton 1996-1997
Copyright (C) Paul Ashton 1997
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _NT_DOMAIN_H /* _NT_DOMAIN_H */
#define _NT_DOMAIN_H
/* dce/rpc support */
#include "rpc_dce.h"
/* miscellaneous structures / defines */
#include "rpc_misc.h"
#include "rpc_creds.h"
#include "talloc.h"
/*
* A bunch of stuff that was put into smb.h
* in the NTDOM branch - it didn't belong there.
*/
typedef struct _prs_struct
{
BOOL io; /* parsing in or out of data stream */
/*
* If the (incoming) data is big-endian. On output we are
* always little-endian.
*/
BOOL bigendian_data;
uint8 align; /* data alignment */
BOOL is_dynamic; /* Do we own this memory or not ? */
uint32 data_offset; /* Current working offset into data. */
uint32 buffer_size; /* Current allocated size of the buffer. */
uint32 grow_size; /* size requested via prs_grow() calls */
char *data_p; /* The buffer itself. */
TALLOC_CTX *mem_ctx; /* When unmarshalling, use this.... */
} prs_struct;
/*
* Defines for io member of prs_struct.
*/
#define MARSHALL 0
#define UNMARSHALL 1
#define MARSHALLING(ps) (!(ps)->io)
#define UNMARSHALLING(ps) ((ps)->io)
#define RPC_BIG_ENDIAN 1
#define RPC_LITTLE_ENDIAN 0
#define RPC_PARSE_ALIGN 4
typedef struct _output_data {
/*
* Raw RPC output data. This does not include RPC headers or footers.
*/
prs_struct rdata;
/* The amount of data sent from the current rdata struct. */
uint32 data_sent_length;
/*
* The current PDU being returned. This inclues
* headers, data and authentication footer.
*/
unsigned char current_pdu[MAX_PDU_FRAG_LEN];
/* The amount of data in the current_pdu buffer. */
uint32 current_pdu_len;
/* The amount of data sent from the current PDU. */
uint32 current_pdu_sent;
} output_data;
typedef struct _input_data {
/*
* This is the current incoming pdu. The data here
* is collected via multiple writes until a complete
* pdu is seen, then the data is copied into the in_data
* structure. The maximum size of this is 0x1630 (MAX_PDU_FRAG_LEN).
*/
unsigned char current_in_pdu[MAX_PDU_FRAG_LEN];
/*
* The amount of data needed to complete the in_pdu.
* If this is zero, then we are at the start of a new
* pdu.
*/
uint32 pdu_needed_len;
/*
* The amount of data received so far in the in_pdu.
* If this is zero, then we are at the start of a new
* pdu.
*/
uint32 pdu_received_len;
/*
* This is the collection of input data with all
* the rpc headers and auth footers removed.
* The maximum length of this (1Mb) is strictly enforced.
*/
prs_struct data;
} input_data;
/*
* Handle database - stored per pipe.
*/
struct policy
{
struct policy *next, *prev;
POLICY_HND pol_hnd;
void *data_ptr;
void (*free_fn)(void *);
};
struct handle_list {
struct policy *Policy; /* List of policies. */
size_t count; /* Current number of handles. */
size_t pipe_ref_count; /* Number of pipe handles referring to this list. */
};
/* Domain controller authentication protocol info */
struct dcinfo
{
DOM_CHAL clnt_chal; /* Initial challenge received from client */
DOM_CHAL srv_chal; /* Initial server challenge */
DOM_CRED clnt_cred; /* Last client credential */
DOM_CRED srv_cred; /* Last server credential */
uchar sess_key[8]; /* Session key */
uchar md4pw[16]; /* md4(machine password) */
fstring mach_acct; /* Machine name we've authenticated. */
fstring remote_machine; /* Machine name we've authenticated. */
BOOL challenge_sent;
BOOL got_session_key;
BOOL authenticated;
};
/*
* DCE/RPC-specific samba-internal-specific handling of data on
* NamedPipes.
*
*/
typedef struct pipes_struct
{
struct pipes_struct *next, *prev;
struct tcon_context *conn;
uint16 vuid; /* points to the unauthenticated user that opened this pipe. */
fstring name;
fstring pipe_srv_name;
RPC_HDR hdr; /* Incoming RPC header. */
RPC_HDR_REQ hdr_req; /* Incoming request header. */
uint32 ntlmssp_chal_flags; /* Client challenge flags. */
BOOL ntlmssp_auth_requested; /* If the client wanted authenticated rpc. */
BOOL ntlmssp_auth_validated; /* If the client *got* authenticated rpc. */
unsigned char challenge[8];
unsigned char ntlmssp_hash[258];
uint32 ntlmssp_seq_num;
struct dcinfo dc; /* Keeps the creds data. */
/*
* Windows user info.
*/
fstring user_name;
fstring domain;
fstring wks;
/*
* Unix user name and credentials.
*/
fstring pipe_user_name;
struct current_user pipe_user;
uint8 session_key[16];
/*
* Set to true when an RPC bind has been done on this pipe.
*/
BOOL pipe_bound;
/*
* Set to true when we should return fault PDU's for everything.
*/
BOOL fault_state;
/*
* Set to true when we should return fault PDU's for a bad handle.
*/
BOOL bad_handle_fault_state;
/*
* Set to RPC_BIG_ENDIAN when dealing with big-endian PDU's
*/
BOOL endian;
/*
* Struct to deal with multiple pdu inputs.
*/
input_data in_data;
/*
* Struct to deal with multiple pdu outputs.
*/
output_data out_data;
/* talloc context to use when allocating memory on this pipe. */
TALLOC_CTX *mem_ctx;
/* handle database to use on this pipe. */
struct handle_list *pipe_handles;
} pipes_struct;
typedef struct smb_np_struct
{
struct smb_np_struct *next, *prev;
int pnum;
struct tcon_context *conn;
uint16 vuid; /* points to the unauthenticated user that opened this pipe. */
BOOL open; /* open connection */
uint16 device_state;
uint16 priority;
fstring name;
/* When replying to an SMBtrans, this is the maximum amount of
data that can be sent in the initial reply. */
int max_trans_reply;
/*
* NamedPipe state information.
*
* (e.g. typecast a np_struct, above).
*/
void *np_state;
/*
* NamedPipe functions, to be called to perform
* Named Pipe transactions on request from an
* SMB client.
*/
/* call to create a named pipe connection.
* returns: state information representing the connection.
* is stored in np_state, above.
*/
void * (*namedpipe_create)(char *pipe_name,
struct tcon_context *conn, uint16 vuid);
/* call to perform a write / read namedpipe transaction.
* TransactNamedPipe is weird: it returns whether there
* is more data outstanding to be read, and the
* caller is expected to take note and follow up with
* read requests.
*/
ssize_t (*namedpipe_transact)(void *np_state,
char *data, int len,
char *rdata, int rlen,
BOOL *pipe_outstanding);
/* call to perform a write namedpipe operation
*/
ssize_t (*namedpipe_write)(void * np_state,
char *data, size_t n);
/* call to perform a read namedpipe operation.
*
* NOTE: the only reason that the pipe_outstanding
* argument is here is because samba does not use
* the namedpipe_transact function yet: instead,
* it performs the same as what namedpipe_transact
* does - a write, followed by a read.
*
* when samba is modified to use namedpipe_transact,
* the pipe_outstanding argument may be removed.
*/
ssize_t (*namedpipe_read)(void * np_state,
char *data, size_t max_len,
BOOL *pipe_outstanding);
/* call to close a namedpipe.
* function is expected to perform all cleanups
* necessary, free all memory etc.
*
* returns True if cleanup was successful (not that
* we particularly care).
*/
BOOL (*namedpipe_close)(void * np_state);
} smb_np_struct;
struct api_struct
{
const char *name;
uint8 opnum;
BOOL (*fn) (pipes_struct *);
};
typedef struct
{
uint32 rid;
const char *name;
} rid_name;
struct acct_info
{
fstring acct_name; /* account name */
fstring acct_desc; /* account name */
uint32 rid; /* domain-relative RID */
};
/*
* higher order functions for use with msrpc client code
*/
#define PRINT_INFO_FN(fn)\
void (*fn)(const char*, uint32, uint32, void *const *const)
#define JOB_INFO_FN(fn)\
void (*fn)(const char*, const char*, uint32, uint32, void *const *const)
/* end higher order functions */
/* security descriptor structures */
#include "rpc_secdes.h"
/* different dce/rpc pipes */
#include "rpc_lsa.h"
#include "rpc_netlogon.h"
#include "rpc_reg.h"
#include "rpc_samr.h"
#include "rpc_srvsvc.h"
#include "rpc_wkssvc.h"
#include "rpc_spoolss.h"
#include "rpc_dfs.h"
#include "rpc_ds.h"
#endif /* _NT_DOMAIN_H */

570
source4/include/nterr.h Normal file
View File

@ -0,0 +1,570 @@
/*
Unix SMB/CIFS implementation.
NT error code constants
Copyright (C) Andrew Tridgell 1992-2000
Copyright (C) John H Terpstra 1996-2000
Copyright (C) Luke Kenneth Casson Leighton 1996-2000
Copyright (C) Paul Ashton 1998-2000
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _NTERR_H
#define _NTERR_H
/* Win32 Status codes. */
#define STATUS_BUFFER_OVERFLOW NT_STATUS(0x80000005)
#define NT_STATUS_NO_MORE_ENTRIES NT_STATUS(0x8000001a)
#define STATUS_MORE_ENTRIES NT_STATUS(0x0105)
#define STATUS_SOME_UNMAPPED NT_STATUS(0x0107)
#define ERROR_INVALID_PARAMETER NT_STATUS(0x0057)
#define ERROR_INSUFFICIENT_BUFFER NT_STATUS(0x007a)
#define STATUS_NOTIFY_ENUM_DIR NT_STATUS(0x010c)
#define ERROR_INVALID_DATATYPE NT_STATUS(0x070c)
/* Win32 Error codes extracted using a loop in smbclient then printing a
netmon sniff to a file. */
/*
--------------
/ \
/ REST \
/ IN \
/ PEACE \
/ \
| NT_STATUS_NOPROBLEMO |
| |
| |
| 4 September |
| |
| 2001 |
*| * * * | *
_________)/\\_//(\/(/\)/\//\/\///|_)_______
*/
#define NT_STATUS_OK NT_STATUS(0x0000)
#define NT_STATUS_UNSUCCESSFUL NT_STATUS(0xC0000000 | 0x0001)
#define NT_STATUS_NOT_IMPLEMENTED NT_STATUS(0xC0000000 | 0x0002)
#define NT_STATUS_INVALID_INFO_CLASS NT_STATUS(0xC0000000 | 0x0003)
#define NT_STATUS_INFO_LENGTH_MISMATCH NT_STATUS(0xC0000000 | 0x0004)
#define NT_STATUS_ACCESS_VIOLATION NT_STATUS(0xC0000000 | 0x0005)
#define NT_STATUS_IN_PAGE_ERROR NT_STATUS(0xC0000000 | 0x0006)
#define NT_STATUS_PAGEFILE_QUOTA NT_STATUS(0xC0000000 | 0x0007)
#define NT_STATUS_INVALID_HANDLE NT_STATUS(0xC0000000 | 0x0008)
#define NT_STATUS_BAD_INITIAL_STACK NT_STATUS(0xC0000000 | 0x0009)
#define NT_STATUS_BAD_INITIAL_PC NT_STATUS(0xC0000000 | 0x000a)
#define NT_STATUS_INVALID_CID NT_STATUS(0xC0000000 | 0x000b)
#define NT_STATUS_TIMER_NOT_CANCELED NT_STATUS(0xC0000000 | 0x000c)
#define NT_STATUS_INVALID_PARAMETER NT_STATUS(0xC0000000 | 0x000d)
#define NT_STATUS_NO_SUCH_DEVICE NT_STATUS(0xC0000000 | 0x000e)
#define NT_STATUS_NO_SUCH_FILE NT_STATUS(0xC0000000 | 0x000f)
#define NT_STATUS_INVALID_DEVICE_REQUEST NT_STATUS(0xC0000000 | 0x0010)
#define NT_STATUS_END_OF_FILE NT_STATUS(0xC0000000 | 0x0011)
#define NT_STATUS_WRONG_VOLUME NT_STATUS(0xC0000000 | 0x0012)
#define NT_STATUS_NO_MEDIA_IN_DEVICE NT_STATUS(0xC0000000 | 0x0013)
#define NT_STATUS_UNRECOGNIZED_MEDIA NT_STATUS(0xC0000000 | 0x0014)
#define NT_STATUS_NONEXISTENT_SECTOR NT_STATUS(0xC0000000 | 0x0015)
#define NT_STATUS_MORE_PROCESSING_REQUIRED NT_STATUS(0xC0000000 | 0x0016)
#define NT_STATUS_NO_MEMORY NT_STATUS(0xC0000000 | 0x0017)
#define NT_STATUS_CONFLICTING_ADDRESSES NT_STATUS(0xC0000000 | 0x0018)
#define NT_STATUS_NOT_MAPPED_VIEW NT_STATUS(0xC0000000 | 0x0019)
#define NT_STATUS_UNABLE_TO_FREE_VM NT_STATUS(0xC0000000 | 0x001a)
#define NT_STATUS_UNABLE_TO_DELETE_SECTION NT_STATUS(0xC0000000 | 0x001b)
#define NT_STATUS_INVALID_SYSTEM_SERVICE NT_STATUS(0xC0000000 | 0x001c)
#define NT_STATUS_ILLEGAL_INSTRUCTION NT_STATUS(0xC0000000 | 0x001d)
#define NT_STATUS_INVALID_LOCK_SEQUENCE NT_STATUS(0xC0000000 | 0x001e)
#define NT_STATUS_INVALID_VIEW_SIZE NT_STATUS(0xC0000000 | 0x001f)
#define NT_STATUS_INVALID_FILE_FOR_SECTION NT_STATUS(0xC0000000 | 0x0020)
#define NT_STATUS_ALREADY_COMMITTED NT_STATUS(0xC0000000 | 0x0021)
#define NT_STATUS_ACCESS_DENIED NT_STATUS(0xC0000000 | 0x0022)
#define NT_STATUS_BUFFER_TOO_SMALL NT_STATUS(0xC0000000 | 0x0023)
#define NT_STATUS_OBJECT_TYPE_MISMATCH NT_STATUS(0xC0000000 | 0x0024)
#define NT_STATUS_NONCONTINUABLE_EXCEPTION NT_STATUS(0xC0000000 | 0x0025)
#define NT_STATUS_INVALID_DISPOSITION NT_STATUS(0xC0000000 | 0x0026)
#define NT_STATUS_UNWIND NT_STATUS(0xC0000000 | 0x0027)
#define NT_STATUS_BAD_STACK NT_STATUS(0xC0000000 | 0x0028)
#define NT_STATUS_INVALID_UNWIND_TARGET NT_STATUS(0xC0000000 | 0x0029)
#define NT_STATUS_NOT_LOCKED NT_STATUS(0xC0000000 | 0x002a)
#define NT_STATUS_PARITY_ERROR NT_STATUS(0xC0000000 | 0x002b)
#define NT_STATUS_UNABLE_TO_DECOMMIT_VM NT_STATUS(0xC0000000 | 0x002c)
#define NT_STATUS_NOT_COMMITTED NT_STATUS(0xC0000000 | 0x002d)
#define NT_STATUS_INVALID_PORT_ATTRIBUTES NT_STATUS(0xC0000000 | 0x002e)
#define NT_STATUS_PORT_MESSAGE_TOO_LONG NT_STATUS(0xC0000000 | 0x002f)
#define NT_STATUS_INVALID_PARAMETER_MIX NT_STATUS(0xC0000000 | 0x0030)
#define NT_STATUS_INVALID_QUOTA_LOWER NT_STATUS(0xC0000000 | 0x0031)
#define NT_STATUS_DISK_CORRUPT_ERROR NT_STATUS(0xC0000000 | 0x0032)
#define NT_STATUS_OBJECT_NAME_INVALID NT_STATUS(0xC0000000 | 0x0033)
#define NT_STATUS_OBJECT_NAME_NOT_FOUND NT_STATUS(0xC0000000 | 0x0034)
#define NT_STATUS_OBJECT_NAME_COLLISION NT_STATUS(0xC0000000 | 0x0035)
#define NT_STATUS_HANDLE_NOT_WAITABLE NT_STATUS(0xC0000000 | 0x0036)
#define NT_STATUS_PORT_DISCONNECTED NT_STATUS(0xC0000000 | 0x0037)
#define NT_STATUS_DEVICE_ALREADY_ATTACHED NT_STATUS(0xC0000000 | 0x0038)
#define NT_STATUS_OBJECT_PATH_INVALID NT_STATUS(0xC0000000 | 0x0039)
#define NT_STATUS_OBJECT_PATH_NOT_FOUND NT_STATUS(0xC0000000 | 0x003a)
#define NT_STATUS_OBJECT_PATH_SYNTAX_BAD NT_STATUS(0xC0000000 | 0x003b)
#define NT_STATUS_DATA_OVERRUN NT_STATUS(0xC0000000 | 0x003c)
#define NT_STATUS_DATA_LATE_ERROR NT_STATUS(0xC0000000 | 0x003d)
#define NT_STATUS_DATA_ERROR NT_STATUS(0xC0000000 | 0x003e)
#define NT_STATUS_CRC_ERROR NT_STATUS(0xC0000000 | 0x003f)
#define NT_STATUS_SECTION_TOO_BIG NT_STATUS(0xC0000000 | 0x0040)
#define NT_STATUS_PORT_CONNECTION_REFUSED NT_STATUS(0xC0000000 | 0x0041)
#define NT_STATUS_INVALID_PORT_HANDLE NT_STATUS(0xC0000000 | 0x0042)
#define NT_STATUS_SHARING_VIOLATION NT_STATUS(0xC0000000 | 0x0043)
#define NT_STATUS_QUOTA_EXCEEDED NT_STATUS(0xC0000000 | 0x0044)
#define NT_STATUS_INVALID_PAGE_PROTECTION NT_STATUS(0xC0000000 | 0x0045)
#define NT_STATUS_MUTANT_NOT_OWNED NT_STATUS(0xC0000000 | 0x0046)
#define NT_STATUS_SEMAPHORE_LIMIT_EXCEEDED NT_STATUS(0xC0000000 | 0x0047)
#define NT_STATUS_PORT_ALREADY_SET NT_STATUS(0xC0000000 | 0x0048)
#define NT_STATUS_SECTION_NOT_IMAGE NT_STATUS(0xC0000000 | 0x0049)
#define NT_STATUS_SUSPEND_COUNT_EXCEEDED NT_STATUS(0xC0000000 | 0x004a)
#define NT_STATUS_THREAD_IS_TERMINATING NT_STATUS(0xC0000000 | 0x004b)
#define NT_STATUS_BAD_WORKING_SET_LIMIT NT_STATUS(0xC0000000 | 0x004c)
#define NT_STATUS_INCOMPATIBLE_FILE_MAP NT_STATUS(0xC0000000 | 0x004d)
#define NT_STATUS_SECTION_PROTECTION NT_STATUS(0xC0000000 | 0x004e)
#define NT_STATUS_EAS_NOT_SUPPORTED NT_STATUS(0xC0000000 | 0x004f)
#define NT_STATUS_EA_TOO_LARGE NT_STATUS(0xC0000000 | 0x0050)
#define NT_STATUS_NONEXISTENT_EA_ENTRY NT_STATUS(0xC0000000 | 0x0051)
#define NT_STATUS_NO_EAS_ON_FILE NT_STATUS(0xC0000000 | 0x0052)
#define NT_STATUS_EA_CORRUPT_ERROR NT_STATUS(0xC0000000 | 0x0053)
#define NT_STATUS_FILE_LOCK_CONFLICT NT_STATUS(0xC0000000 | 0x0054)
#define NT_STATUS_LOCK_NOT_GRANTED NT_STATUS(0xC0000000 | 0x0055)
#define NT_STATUS_DELETE_PENDING NT_STATUS(0xC0000000 | 0x0056)
#define NT_STATUS_CTL_FILE_NOT_SUPPORTED NT_STATUS(0xC0000000 | 0x0057)
#define NT_STATUS_UNKNOWN_REVISION NT_STATUS(0xC0000000 | 0x0058)
#define NT_STATUS_REVISION_MISMATCH NT_STATUS(0xC0000000 | 0x0059)
#define NT_STATUS_INVALID_OWNER NT_STATUS(0xC0000000 | 0x005a)
#define NT_STATUS_INVALID_PRIMARY_GROUP NT_STATUS(0xC0000000 | 0x005b)
#define NT_STATUS_NO_IMPERSONATION_TOKEN NT_STATUS(0xC0000000 | 0x005c)
#define NT_STATUS_CANT_DISABLE_MANDATORY NT_STATUS(0xC0000000 | 0x005d)
#define NT_STATUS_NO_LOGON_SERVERS NT_STATUS(0xC0000000 | 0x005e)
#define NT_STATUS_NO_SUCH_LOGON_SESSION NT_STATUS(0xC0000000 | 0x005f)
#define NT_STATUS_NO_SUCH_PRIVILEGE NT_STATUS(0xC0000000 | 0x0060)
#define NT_STATUS_PRIVILEGE_NOT_HELD NT_STATUS(0xC0000000 | 0x0061)
#define NT_STATUS_INVALID_ACCOUNT_NAME NT_STATUS(0xC0000000 | 0x0062)
#define NT_STATUS_USER_EXISTS NT_STATUS(0xC0000000 | 0x0063)
#define NT_STATUS_NO_SUCH_USER NT_STATUS(0xC0000000 | 0x0064)
#define NT_STATUS_GROUP_EXISTS NT_STATUS(0xC0000000 | 0x0065)
#define NT_STATUS_NO_SUCH_GROUP NT_STATUS(0xC0000000 | 0x0066)
#define NT_STATUS_MEMBER_IN_GROUP NT_STATUS(0xC0000000 | 0x0067)
#define NT_STATUS_MEMBER_NOT_IN_GROUP NT_STATUS(0xC0000000 | 0x0068)
#define NT_STATUS_LAST_ADMIN NT_STATUS(0xC0000000 | 0x0069)
#define NT_STATUS_WRONG_PASSWORD NT_STATUS(0xC0000000 | 0x006a)
#define NT_STATUS_ILL_FORMED_PASSWORD NT_STATUS(0xC0000000 | 0x006b)
#define NT_STATUS_PASSWORD_RESTRICTION NT_STATUS(0xC0000000 | 0x006c)
#define NT_STATUS_LOGON_FAILURE NT_STATUS(0xC0000000 | 0x006d)
#define NT_STATUS_ACCOUNT_RESTRICTION NT_STATUS(0xC0000000 | 0x006e)
#define NT_STATUS_INVALID_LOGON_HOURS NT_STATUS(0xC0000000 | 0x006f)
#define NT_STATUS_INVALID_WORKSTATION NT_STATUS(0xC0000000 | 0x0070)
#define NT_STATUS_PASSWORD_EXPIRED NT_STATUS(0xC0000000 | 0x0071)
#define NT_STATUS_ACCOUNT_DISABLED NT_STATUS(0xC0000000 | 0x0072)
#define NT_STATUS_NONE_MAPPED NT_STATUS(0xC0000000 | 0x0073)
#define NT_STATUS_TOO_MANY_LUIDS_REQUESTED NT_STATUS(0xC0000000 | 0x0074)
#define NT_STATUS_LUIDS_EXHAUSTED NT_STATUS(0xC0000000 | 0x0075)
#define NT_STATUS_INVALID_SUB_AUTHORITY NT_STATUS(0xC0000000 | 0x0076)
#define NT_STATUS_INVALID_ACL NT_STATUS(0xC0000000 | 0x0077)
#define NT_STATUS_INVALID_SID NT_STATUS(0xC0000000 | 0x0078)
#define NT_STATUS_INVALID_SECURITY_DESCR NT_STATUS(0xC0000000 | 0x0079)
#define NT_STATUS_PROCEDURE_NOT_FOUND NT_STATUS(0xC0000000 | 0x007a)
#define NT_STATUS_INVALID_IMAGE_FORMAT NT_STATUS(0xC0000000 | 0x007b)
#define NT_STATUS_NO_TOKEN NT_STATUS(0xC0000000 | 0x007c)
#define NT_STATUS_BAD_INHERITANCE_ACL NT_STATUS(0xC0000000 | 0x007d)
#define NT_STATUS_RANGE_NOT_LOCKED NT_STATUS(0xC0000000 | 0x007e)
#define NT_STATUS_DISK_FULL NT_STATUS(0xC0000000 | 0x007f)
#define NT_STATUS_SERVER_DISABLED NT_STATUS(0xC0000000 | 0x0080)
#define NT_STATUS_SERVER_NOT_DISABLED NT_STATUS(0xC0000000 | 0x0081)
#define NT_STATUS_TOO_MANY_GUIDS_REQUESTED NT_STATUS(0xC0000000 | 0x0082)
#define NT_STATUS_GUIDS_EXHAUSTED NT_STATUS(0xC0000000 | 0x0083)
#define NT_STATUS_INVALID_ID_AUTHORITY NT_STATUS(0xC0000000 | 0x0084)
#define NT_STATUS_AGENTS_EXHAUSTED NT_STATUS(0xC0000000 | 0x0085)
#define NT_STATUS_INVALID_VOLUME_LABEL NT_STATUS(0xC0000000 | 0x0086)
#define NT_STATUS_SECTION_NOT_EXTENDED NT_STATUS(0xC0000000 | 0x0087)
#define NT_STATUS_NOT_MAPPED_DATA NT_STATUS(0xC0000000 | 0x0088)
#define NT_STATUS_RESOURCE_DATA_NOT_FOUND NT_STATUS(0xC0000000 | 0x0089)
#define NT_STATUS_RESOURCE_TYPE_NOT_FOUND NT_STATUS(0xC0000000 | 0x008a)
#define NT_STATUS_RESOURCE_NAME_NOT_FOUND NT_STATUS(0xC0000000 | 0x008b)
#define NT_STATUS_ARRAY_BOUNDS_EXCEEDED NT_STATUS(0xC0000000 | 0x008c)
#define NT_STATUS_FLOAT_DENORMAL_OPERAND NT_STATUS(0xC0000000 | 0x008d)
#define NT_STATUS_FLOAT_DIVIDE_BY_ZERO NT_STATUS(0xC0000000 | 0x008e)
#define NT_STATUS_FLOAT_INEXACT_RESULT NT_STATUS(0xC0000000 | 0x008f)
#define NT_STATUS_FLOAT_INVALID_OPERATION NT_STATUS(0xC0000000 | 0x0090)
#define NT_STATUS_FLOAT_OVERFLOW NT_STATUS(0xC0000000 | 0x0091)
#define NT_STATUS_FLOAT_STACK_CHECK NT_STATUS(0xC0000000 | 0x0092)
#define NT_STATUS_FLOAT_UNDERFLOW NT_STATUS(0xC0000000 | 0x0093)
#define NT_STATUS_INTEGER_DIVIDE_BY_ZERO NT_STATUS(0xC0000000 | 0x0094)
#define NT_STATUS_INTEGER_OVERFLOW NT_STATUS(0xC0000000 | 0x0095)
#define NT_STATUS_PRIVILEGED_INSTRUCTION NT_STATUS(0xC0000000 | 0x0096)
#define NT_STATUS_TOO_MANY_PAGING_FILES NT_STATUS(0xC0000000 | 0x0097)
#define NT_STATUS_FILE_INVALID NT_STATUS(0xC0000000 | 0x0098)
#define NT_STATUS_ALLOTTED_SPACE_EXCEEDED NT_STATUS(0xC0000000 | 0x0099)
#define NT_STATUS_INSUFFICIENT_RESOURCES NT_STATUS(0xC0000000 | 0x009a)
#define NT_STATUS_DFS_EXIT_PATH_FOUND NT_STATUS(0xC0000000 | 0x009b)
#define NT_STATUS_DEVICE_DATA_ERROR NT_STATUS(0xC0000000 | 0x009c)
#define NT_STATUS_DEVICE_NOT_CONNECTED NT_STATUS(0xC0000000 | 0x009d)
#define NT_STATUS_DEVICE_POWER_FAILURE NT_STATUS(0xC0000000 | 0x009e)
#define NT_STATUS_FREE_VM_NOT_AT_BASE NT_STATUS(0xC0000000 | 0x009f)
#define NT_STATUS_MEMORY_NOT_ALLOCATED NT_STATUS(0xC0000000 | 0x00a0)
#define NT_STATUS_WORKING_SET_QUOTA NT_STATUS(0xC0000000 | 0x00a1)
#define NT_STATUS_MEDIA_WRITE_PROTECTED NT_STATUS(0xC0000000 | 0x00a2)
#define NT_STATUS_DEVICE_NOT_READY NT_STATUS(0xC0000000 | 0x00a3)
#define NT_STATUS_INVALID_GROUP_ATTRIBUTES NT_STATUS(0xC0000000 | 0x00a4)
#define NT_STATUS_BAD_IMPERSONATION_LEVEL NT_STATUS(0xC0000000 | 0x00a5)
#define NT_STATUS_CANT_OPEN_ANONYMOUS NT_STATUS(0xC0000000 | 0x00a6)
#define NT_STATUS_BAD_VALIDATION_CLASS NT_STATUS(0xC0000000 | 0x00a7)
#define NT_STATUS_BAD_TOKEN_TYPE NT_STATUS(0xC0000000 | 0x00a8)
#define NT_STATUS_BAD_MASTER_BOOT_RECORD NT_STATUS(0xC0000000 | 0x00a9)
#define NT_STATUS_INSTRUCTION_MISALIGNMENT NT_STATUS(0xC0000000 | 0x00aa)
#define NT_STATUS_INSTANCE_NOT_AVAILABLE NT_STATUS(0xC0000000 | 0x00ab)
#define NT_STATUS_PIPE_NOT_AVAILABLE NT_STATUS(0xC0000000 | 0x00ac)
#define NT_STATUS_INVALID_PIPE_STATE NT_STATUS(0xC0000000 | 0x00ad)
#define NT_STATUS_PIPE_BUSY NT_STATUS(0xC0000000 | 0x00ae)
#define NT_STATUS_ILLEGAL_FUNCTION NT_STATUS(0xC0000000 | 0x00af)
#define NT_STATUS_PIPE_DISCONNECTED NT_STATUS(0xC0000000 | 0x00b0)
#define NT_STATUS_PIPE_CLOSING NT_STATUS(0xC0000000 | 0x00b1)
#define NT_STATUS_PIPE_CONNECTED NT_STATUS(0xC0000000 | 0x00b2)
#define NT_STATUS_PIPE_LISTENING NT_STATUS(0xC0000000 | 0x00b3)
#define NT_STATUS_INVALID_READ_MODE NT_STATUS(0xC0000000 | 0x00b4)
#define NT_STATUS_IO_TIMEOUT NT_STATUS(0xC0000000 | 0x00b5)
#define NT_STATUS_FILE_FORCED_CLOSED NT_STATUS(0xC0000000 | 0x00b6)
#define NT_STATUS_PROFILING_NOT_STARTED NT_STATUS(0xC0000000 | 0x00b7)
#define NT_STATUS_PROFILING_NOT_STOPPED NT_STATUS(0xC0000000 | 0x00b8)
#define NT_STATUS_COULD_NOT_INTERPRET NT_STATUS(0xC0000000 | 0x00b9)
#define NT_STATUS_FILE_IS_A_DIRECTORY NT_STATUS(0xC0000000 | 0x00ba)
#define NT_STATUS_NOT_SUPPORTED NT_STATUS(0xC0000000 | 0x00bb)
#define NT_STATUS_REMOTE_NOT_LISTENING NT_STATUS(0xC0000000 | 0x00bc)
#define NT_STATUS_DUPLICATE_NAME NT_STATUS(0xC0000000 | 0x00bd)
#define NT_STATUS_BAD_NETWORK_PATH NT_STATUS(0xC0000000 | 0x00be)
#define NT_STATUS_NETWORK_BUSY NT_STATUS(0xC0000000 | 0x00bf)
#define NT_STATUS_DEVICE_DOES_NOT_EXIST NT_STATUS(0xC0000000 | 0x00c0)
#define NT_STATUS_TOO_MANY_COMMANDS NT_STATUS(0xC0000000 | 0x00c1)
#define NT_STATUS_ADAPTER_HARDWARE_ERROR NT_STATUS(0xC0000000 | 0x00c2)
#define NT_STATUS_INVALID_NETWORK_RESPONSE NT_STATUS(0xC0000000 | 0x00c3)
#define NT_STATUS_UNEXPECTED_NETWORK_ERROR NT_STATUS(0xC0000000 | 0x00c4)
#define NT_STATUS_BAD_REMOTE_ADAPTER NT_STATUS(0xC0000000 | 0x00c5)
#define NT_STATUS_PRINT_QUEUE_FULL NT_STATUS(0xC0000000 | 0x00c6)
#define NT_STATUS_NO_SPOOL_SPACE NT_STATUS(0xC0000000 | 0x00c7)
#define NT_STATUS_PRINT_CANCELLED NT_STATUS(0xC0000000 | 0x00c8)
#define NT_STATUS_NETWORK_NAME_DELETED NT_STATUS(0xC0000000 | 0x00c9)
#define NT_STATUS_NETWORK_ACCESS_DENIED NT_STATUS(0xC0000000 | 0x00ca)
#define NT_STATUS_BAD_DEVICE_TYPE NT_STATUS(0xC0000000 | 0x00cb)
#define NT_STATUS_BAD_NETWORK_NAME NT_STATUS(0xC0000000 | 0x00cc)
#define NT_STATUS_TOO_MANY_NAMES NT_STATUS(0xC0000000 | 0x00cd)
#define NT_STATUS_TOO_MANY_SESSIONS NT_STATUS(0xC0000000 | 0x00ce)
#define NT_STATUS_SHARING_PAUSED NT_STATUS(0xC0000000 | 0x00cf)
#define NT_STATUS_REQUEST_NOT_ACCEPTED NT_STATUS(0xC0000000 | 0x00d0)
#define NT_STATUS_REDIRECTOR_PAUSED NT_STATUS(0xC0000000 | 0x00d1)
#define NT_STATUS_NET_WRITE_FAULT NT_STATUS(0xC0000000 | 0x00d2)
#define NT_STATUS_PROFILING_AT_LIMIT NT_STATUS(0xC0000000 | 0x00d3)
#define NT_STATUS_NOT_SAME_DEVICE NT_STATUS(0xC0000000 | 0x00d4)
#define NT_STATUS_FILE_RENAMED NT_STATUS(0xC0000000 | 0x00d5)
#define NT_STATUS_VIRTUAL_CIRCUIT_CLOSED NT_STATUS(0xC0000000 | 0x00d6)
#define NT_STATUS_NO_SECURITY_ON_OBJECT NT_STATUS(0xC0000000 | 0x00d7)
#define NT_STATUS_CANT_WAIT NT_STATUS(0xC0000000 | 0x00d8)
#define NT_STATUS_PIPE_EMPTY NT_STATUS(0xC0000000 | 0x00d9)
#define NT_STATUS_CANT_ACCESS_DOMAIN_INFO NT_STATUS(0xC0000000 | 0x00da)
#define NT_STATUS_CANT_TERMINATE_SELF NT_STATUS(0xC0000000 | 0x00db)
#define NT_STATUS_INVALID_SERVER_STATE NT_STATUS(0xC0000000 | 0x00dc)
#define NT_STATUS_INVALID_DOMAIN_STATE NT_STATUS(0xC0000000 | 0x00dd)
#define NT_STATUS_INVALID_DOMAIN_ROLE NT_STATUS(0xC0000000 | 0x00de)
#define NT_STATUS_NO_SUCH_DOMAIN NT_STATUS(0xC0000000 | 0x00df)
#define NT_STATUS_DOMAIN_EXISTS NT_STATUS(0xC0000000 | 0x00e0)
#define NT_STATUS_DOMAIN_LIMIT_EXCEEDED NT_STATUS(0xC0000000 | 0x00e1)
#define NT_STATUS_OPLOCK_NOT_GRANTED NT_STATUS(0xC0000000 | 0x00e2)
#define NT_STATUS_INVALID_OPLOCK_PROTOCOL NT_STATUS(0xC0000000 | 0x00e3)
#define NT_STATUS_INTERNAL_DB_CORRUPTION NT_STATUS(0xC0000000 | 0x00e4)
#define NT_STATUS_INTERNAL_ERROR NT_STATUS(0xC0000000 | 0x00e5)
#define NT_STATUS_GENERIC_NOT_MAPPED NT_STATUS(0xC0000000 | 0x00e6)
#define NT_STATUS_BAD_DESCRIPTOR_FORMAT NT_STATUS(0xC0000000 | 0x00e7)
#define NT_STATUS_INVALID_USER_BUFFER NT_STATUS(0xC0000000 | 0x00e8)
#define NT_STATUS_UNEXPECTED_IO_ERROR NT_STATUS(0xC0000000 | 0x00e9)
#define NT_STATUS_UNEXPECTED_MM_CREATE_ERR NT_STATUS(0xC0000000 | 0x00ea)
#define NT_STATUS_UNEXPECTED_MM_MAP_ERROR NT_STATUS(0xC0000000 | 0x00eb)
#define NT_STATUS_UNEXPECTED_MM_EXTEND_ERR NT_STATUS(0xC0000000 | 0x00ec)
#define NT_STATUS_NOT_LOGON_PROCESS NT_STATUS(0xC0000000 | 0x00ed)
#define NT_STATUS_LOGON_SESSION_EXISTS NT_STATUS(0xC0000000 | 0x00ee)
#define NT_STATUS_INVALID_PARAMETER_1 NT_STATUS(0xC0000000 | 0x00ef)
#define NT_STATUS_INVALID_PARAMETER_2 NT_STATUS(0xC0000000 | 0x00f0)
#define NT_STATUS_INVALID_PARAMETER_3 NT_STATUS(0xC0000000 | 0x00f1)
#define NT_STATUS_INVALID_PARAMETER_4 NT_STATUS(0xC0000000 | 0x00f2)
#define NT_STATUS_INVALID_PARAMETER_5 NT_STATUS(0xC0000000 | 0x00f3)
#define NT_STATUS_INVALID_PARAMETER_6 NT_STATUS(0xC0000000 | 0x00f4)
#define NT_STATUS_INVALID_PARAMETER_7 NT_STATUS(0xC0000000 | 0x00f5)
#define NT_STATUS_INVALID_PARAMETER_8 NT_STATUS(0xC0000000 | 0x00f6)
#define NT_STATUS_INVALID_PARAMETER_9 NT_STATUS(0xC0000000 | 0x00f7)
#define NT_STATUS_INVALID_PARAMETER_10 NT_STATUS(0xC0000000 | 0x00f8)
#define NT_STATUS_INVALID_PARAMETER_11 NT_STATUS(0xC0000000 | 0x00f9)
#define NT_STATUS_INVALID_PARAMETER_12 NT_STATUS(0xC0000000 | 0x00fa)
#define NT_STATUS_REDIRECTOR_NOT_STARTED NT_STATUS(0xC0000000 | 0x00fb)
#define NT_STATUS_REDIRECTOR_STARTED NT_STATUS(0xC0000000 | 0x00fc)
#define NT_STATUS_STACK_OVERFLOW NT_STATUS(0xC0000000 | 0x00fd)
#define NT_STATUS_NO_SUCH_PACKAGE NT_STATUS(0xC0000000 | 0x00fe)
#define NT_STATUS_BAD_FUNCTION_TABLE NT_STATUS(0xC0000000 | 0x00ff)
#define NT_STATUS_DIRECTORY_NOT_EMPTY NT_STATUS(0xC0000000 | 0x0101)
#define NT_STATUS_FILE_CORRUPT_ERROR NT_STATUS(0xC0000000 | 0x0102)
#define NT_STATUS_NOT_A_DIRECTORY NT_STATUS(0xC0000000 | 0x0103)
#define NT_STATUS_BAD_LOGON_SESSION_STATE NT_STATUS(0xC0000000 | 0x0104)
#define NT_STATUS_LOGON_SESSION_COLLISION NT_STATUS(0xC0000000 | 0x0105)
#define NT_STATUS_NAME_TOO_LONG NT_STATUS(0xC0000000 | 0x0106)
#define NT_STATUS_FILES_OPEN NT_STATUS(0xC0000000 | 0x0107)
#define NT_STATUS_CONNECTION_IN_USE NT_STATUS(0xC0000000 | 0x0108)
#define NT_STATUS_MESSAGE_NOT_FOUND NT_STATUS(0xC0000000 | 0x0109)
#define NT_STATUS_PROCESS_IS_TERMINATING NT_STATUS(0xC0000000 | 0x010a)
#define NT_STATUS_INVALID_LOGON_TYPE NT_STATUS(0xC0000000 | 0x010b)
#define NT_STATUS_NO_GUID_TRANSLATION NT_STATUS(0xC0000000 | 0x010c)
#define NT_STATUS_CANNOT_IMPERSONATE NT_STATUS(0xC0000000 | 0x010d)
#define NT_STATUS_IMAGE_ALREADY_LOADED NT_STATUS(0xC0000000 | 0x010e)
#define NT_STATUS_ABIOS_NOT_PRESENT NT_STATUS(0xC0000000 | 0x010f)
#define NT_STATUS_ABIOS_LID_NOT_EXIST NT_STATUS(0xC0000000 | 0x0110)
#define NT_STATUS_ABIOS_LID_ALREADY_OWNED NT_STATUS(0xC0000000 | 0x0111)
#define NT_STATUS_ABIOS_NOT_LID_OWNER NT_STATUS(0xC0000000 | 0x0112)
#define NT_STATUS_ABIOS_INVALID_COMMAND NT_STATUS(0xC0000000 | 0x0113)
#define NT_STATUS_ABIOS_INVALID_LID NT_STATUS(0xC0000000 | 0x0114)
#define NT_STATUS_ABIOS_SELECTOR_NOT_AVAILABLE NT_STATUS(0xC0000000 | 0x0115)
#define NT_STATUS_ABIOS_INVALID_SELECTOR NT_STATUS(0xC0000000 | 0x0116)
#define NT_STATUS_NO_LDT NT_STATUS(0xC0000000 | 0x0117)
#define NT_STATUS_INVALID_LDT_SIZE NT_STATUS(0xC0000000 | 0x0118)
#define NT_STATUS_INVALID_LDT_OFFSET NT_STATUS(0xC0000000 | 0x0119)
#define NT_STATUS_INVALID_LDT_DESCRIPTOR NT_STATUS(0xC0000000 | 0x011a)
#define NT_STATUS_INVALID_IMAGE_NE_FORMAT NT_STATUS(0xC0000000 | 0x011b)
#define NT_STATUS_RXACT_INVALID_STATE NT_STATUS(0xC0000000 | 0x011c)
#define NT_STATUS_RXACT_COMMIT_FAILURE NT_STATUS(0xC0000000 | 0x011d)
#define NT_STATUS_MAPPED_FILE_SIZE_ZERO NT_STATUS(0xC0000000 | 0x011e)
#define NT_STATUS_TOO_MANY_OPENED_FILES NT_STATUS(0xC0000000 | 0x011f)
#define NT_STATUS_CANCELLED NT_STATUS(0xC0000000 | 0x0120)
#define NT_STATUS_CANNOT_DELETE NT_STATUS(0xC0000000 | 0x0121)
#define NT_STATUS_INVALID_COMPUTER_NAME NT_STATUS(0xC0000000 | 0x0122)
#define NT_STATUS_FILE_DELETED NT_STATUS(0xC0000000 | 0x0123)
#define NT_STATUS_SPECIAL_ACCOUNT NT_STATUS(0xC0000000 | 0x0124)
#define NT_STATUS_SPECIAL_GROUP NT_STATUS(0xC0000000 | 0x0125)
#define NT_STATUS_SPECIAL_USER NT_STATUS(0xC0000000 | 0x0126)
#define NT_STATUS_MEMBERS_PRIMARY_GROUP NT_STATUS(0xC0000000 | 0x0127)
#define NT_STATUS_FILE_CLOSED NT_STATUS(0xC0000000 | 0x0128)
#define NT_STATUS_TOO_MANY_THREADS NT_STATUS(0xC0000000 | 0x0129)
#define NT_STATUS_THREAD_NOT_IN_PROCESS NT_STATUS(0xC0000000 | 0x012a)
#define NT_STATUS_TOKEN_ALREADY_IN_USE NT_STATUS(0xC0000000 | 0x012b)
#define NT_STATUS_PAGEFILE_QUOTA_EXCEEDED NT_STATUS(0xC0000000 | 0x012c)
#define NT_STATUS_COMMITMENT_LIMIT NT_STATUS(0xC0000000 | 0x012d)
#define NT_STATUS_INVALID_IMAGE_LE_FORMAT NT_STATUS(0xC0000000 | 0x012e)
#define NT_STATUS_INVALID_IMAGE_NOT_MZ NT_STATUS(0xC0000000 | 0x012f)
#define NT_STATUS_INVALID_IMAGE_PROTECT NT_STATUS(0xC0000000 | 0x0130)
#define NT_STATUS_INVALID_IMAGE_WIN_16 NT_STATUS(0xC0000000 | 0x0131)
#define NT_STATUS_LOGON_SERVER_CONFLICT NT_STATUS(0xC0000000 | 0x0132)
#define NT_STATUS_TIME_DIFFERENCE_AT_DC NT_STATUS(0xC0000000 | 0x0133)
#define NT_STATUS_SYNCHRONIZATION_REQUIRED NT_STATUS(0xC0000000 | 0x0134)
#define NT_STATUS_DLL_NOT_FOUND NT_STATUS(0xC0000000 | 0x0135)
#define NT_STATUS_OPEN_FAILED NT_STATUS(0xC0000000 | 0x0136)
#define NT_STATUS_IO_PRIVILEGE_FAILED NT_STATUS(0xC0000000 | 0x0137)
#define NT_STATUS_ORDINAL_NOT_FOUND NT_STATUS(0xC0000000 | 0x0138)
#define NT_STATUS_ENTRYPOINT_NOT_FOUND NT_STATUS(0xC0000000 | 0x0139)
#define NT_STATUS_CONTROL_C_EXIT NT_STATUS(0xC0000000 | 0x013a)
#define NT_STATUS_LOCAL_DISCONNECT NT_STATUS(0xC0000000 | 0x013b)
#define NT_STATUS_REMOTE_DISCONNECT NT_STATUS(0xC0000000 | 0x013c)
#define NT_STATUS_REMOTE_RESOURCES NT_STATUS(0xC0000000 | 0x013d)
#define NT_STATUS_LINK_FAILED NT_STATUS(0xC0000000 | 0x013e)
#define NT_STATUS_LINK_TIMEOUT NT_STATUS(0xC0000000 | 0x013f)
#define NT_STATUS_INVALID_CONNECTION NT_STATUS(0xC0000000 | 0x0140)
#define NT_STATUS_INVALID_ADDRESS NT_STATUS(0xC0000000 | 0x0141)
#define NT_STATUS_DLL_INIT_FAILED NT_STATUS(0xC0000000 | 0x0142)
#define NT_STATUS_MISSING_SYSTEMFILE NT_STATUS(0xC0000000 | 0x0143)
#define NT_STATUS_UNHANDLED_EXCEPTION NT_STATUS(0xC0000000 | 0x0144)
#define NT_STATUS_APP_INIT_FAILURE NT_STATUS(0xC0000000 | 0x0145)
#define NT_STATUS_PAGEFILE_CREATE_FAILED NT_STATUS(0xC0000000 | 0x0146)
#define NT_STATUS_NO_PAGEFILE NT_STATUS(0xC0000000 | 0x0147)
#define NT_STATUS_INVALID_LEVEL NT_STATUS(0xC0000000 | 0x0148)
#define NT_STATUS_WRONG_PASSWORD_CORE NT_STATUS(0xC0000000 | 0x0149)
#define NT_STATUS_ILLEGAL_FLOAT_CONTEXT NT_STATUS(0xC0000000 | 0x014a)
#define NT_STATUS_PIPE_BROKEN NT_STATUS(0xC0000000 | 0x014b)
#define NT_STATUS_REGISTRY_CORRUPT NT_STATUS(0xC0000000 | 0x014c)
#define NT_STATUS_REGISTRY_IO_FAILED NT_STATUS(0xC0000000 | 0x014d)
#define NT_STATUS_NO_EVENT_PAIR NT_STATUS(0xC0000000 | 0x014e)
#define NT_STATUS_UNRECOGNIZED_VOLUME NT_STATUS(0xC0000000 | 0x014f)
#define NT_STATUS_SERIAL_NO_DEVICE_INITED NT_STATUS(0xC0000000 | 0x0150)
#define NT_STATUS_NO_SUCH_ALIAS NT_STATUS(0xC0000000 | 0x0151)
#define NT_STATUS_MEMBER_NOT_IN_ALIAS NT_STATUS(0xC0000000 | 0x0152)
#define NT_STATUS_MEMBER_IN_ALIAS NT_STATUS(0xC0000000 | 0x0153)
#define NT_STATUS_ALIAS_EXISTS NT_STATUS(0xC0000000 | 0x0154)
#define NT_STATUS_LOGON_NOT_GRANTED NT_STATUS(0xC0000000 | 0x0155)
#define NT_STATUS_TOO_MANY_SECRETS NT_STATUS(0xC0000000 | 0x0156)
#define NT_STATUS_SECRET_TOO_LONG NT_STATUS(0xC0000000 | 0x0157)
#define NT_STATUS_INTERNAL_DB_ERROR NT_STATUS(0xC0000000 | 0x0158)
#define NT_STATUS_FULLSCREEN_MODE NT_STATUS(0xC0000000 | 0x0159)
#define NT_STATUS_TOO_MANY_CONTEXT_IDS NT_STATUS(0xC0000000 | 0x015a)
#define NT_STATUS_LOGON_TYPE_NOT_GRANTED NT_STATUS(0xC0000000 | 0x015b)
#define NT_STATUS_NOT_REGISTRY_FILE NT_STATUS(0xC0000000 | 0x015c)
#define NT_STATUS_NT_CROSS_ENCRYPTION_REQUIRED NT_STATUS(0xC0000000 | 0x015d)
#define NT_STATUS_DOMAIN_CTRLR_CONFIG_ERROR NT_STATUS(0xC0000000 | 0x015e)
#define NT_STATUS_FT_MISSING_MEMBER NT_STATUS(0xC0000000 | 0x015f)
#define NT_STATUS_ILL_FORMED_SERVICE_ENTRY NT_STATUS(0xC0000000 | 0x0160)
#define NT_STATUS_ILLEGAL_CHARACTER NT_STATUS(0xC0000000 | 0x0161)
#define NT_STATUS_UNMAPPABLE_CHARACTER NT_STATUS(0xC0000000 | 0x0162)
#define NT_STATUS_UNDEFINED_CHARACTER NT_STATUS(0xC0000000 | 0x0163)
#define NT_STATUS_FLOPPY_VOLUME NT_STATUS(0xC0000000 | 0x0164)
#define NT_STATUS_FLOPPY_ID_MARK_NOT_FOUND NT_STATUS(0xC0000000 | 0x0165)
#define NT_STATUS_FLOPPY_WRONG_CYLINDER NT_STATUS(0xC0000000 | 0x0166)
#define NT_STATUS_FLOPPY_UNKNOWN_ERROR NT_STATUS(0xC0000000 | 0x0167)
#define NT_STATUS_FLOPPY_BAD_REGISTERS NT_STATUS(0xC0000000 | 0x0168)
#define NT_STATUS_DISK_RECALIBRATE_FAILED NT_STATUS(0xC0000000 | 0x0169)
#define NT_STATUS_DISK_OPERATION_FAILED NT_STATUS(0xC0000000 | 0x016a)
#define NT_STATUS_DISK_RESET_FAILED NT_STATUS(0xC0000000 | 0x016b)
#define NT_STATUS_SHARED_IRQ_BUSY NT_STATUS(0xC0000000 | 0x016c)
#define NT_STATUS_FT_ORPHANING NT_STATUS(0xC0000000 | 0x016d)
#define NT_STATUS_PARTITION_FAILURE NT_STATUS(0xC0000000 | 0x0172)
#define NT_STATUS_INVALID_BLOCK_LENGTH NT_STATUS(0xC0000000 | 0x0173)
#define NT_STATUS_DEVICE_NOT_PARTITIONED NT_STATUS(0xC0000000 | 0x0174)
#define NT_STATUS_UNABLE_TO_LOCK_MEDIA NT_STATUS(0xC0000000 | 0x0175)
#define NT_STATUS_UNABLE_TO_UNLOAD_MEDIA NT_STATUS(0xC0000000 | 0x0176)
#define NT_STATUS_EOM_OVERFLOW NT_STATUS(0xC0000000 | 0x0177)
#define NT_STATUS_NO_MEDIA NT_STATUS(0xC0000000 | 0x0178)
#define NT_STATUS_NO_SUCH_MEMBER NT_STATUS(0xC0000000 | 0x017a)
#define NT_STATUS_INVALID_MEMBER NT_STATUS(0xC0000000 | 0x017b)
#define NT_STATUS_KEY_DELETED NT_STATUS(0xC0000000 | 0x017c)
#define NT_STATUS_NO_LOG_SPACE NT_STATUS(0xC0000000 | 0x017d)
#define NT_STATUS_TOO_MANY_SIDS NT_STATUS(0xC0000000 | 0x017e)
#define NT_STATUS_LM_CROSS_ENCRYPTION_REQUIRED NT_STATUS(0xC0000000 | 0x017f)
#define NT_STATUS_KEY_HAS_CHILDREN NT_STATUS(0xC0000000 | 0x0180)
#define NT_STATUS_CHILD_MUST_BE_VOLATILE NT_STATUS(0xC0000000 | 0x0181)
#define NT_STATUS_DEVICE_CONFIGURATION_ERROR NT_STATUS(0xC0000000 | 0x0182)
#define NT_STATUS_DRIVER_INTERNAL_ERROR NT_STATUS(0xC0000000 | 0x0183)
#define NT_STATUS_INVALID_DEVICE_STATE NT_STATUS(0xC0000000 | 0x0184)
#define NT_STATUS_IO_DEVICE_ERROR NT_STATUS(0xC0000000 | 0x0185)
#define NT_STATUS_DEVICE_PROTOCOL_ERROR NT_STATUS(0xC0000000 | 0x0186)
#define NT_STATUS_BACKUP_CONTROLLER NT_STATUS(0xC0000000 | 0x0187)
#define NT_STATUS_LOG_FILE_FULL NT_STATUS(0xC0000000 | 0x0188)
#define NT_STATUS_TOO_LATE NT_STATUS(0xC0000000 | 0x0189)
#define NT_STATUS_NO_TRUST_LSA_SECRET NT_STATUS(0xC0000000 | 0x018a)
#define NT_STATUS_NO_TRUST_SAM_ACCOUNT NT_STATUS(0xC0000000 | 0x018b)
#define NT_STATUS_TRUSTED_DOMAIN_FAILURE NT_STATUS(0xC0000000 | 0x018c)
#define NT_STATUS_TRUSTED_RELATIONSHIP_FAILURE NT_STATUS(0xC0000000 | 0x018d)
#define NT_STATUS_EVENTLOG_FILE_CORRUPT NT_STATUS(0xC0000000 | 0x018e)
#define NT_STATUS_EVENTLOG_CANT_START NT_STATUS(0xC0000000 | 0x018f)
#define NT_STATUS_TRUST_FAILURE NT_STATUS(0xC0000000 | 0x0190)
#define NT_STATUS_MUTANT_LIMIT_EXCEEDED NT_STATUS(0xC0000000 | 0x0191)
#define NT_STATUS_NETLOGON_NOT_STARTED NT_STATUS(0xC0000000 | 0x0192)
#define NT_STATUS_ACCOUNT_EXPIRED NT_STATUS(0xC0000000 | 0x0193)
#define NT_STATUS_POSSIBLE_DEADLOCK NT_STATUS(0xC0000000 | 0x0194)
#define NT_STATUS_NETWORK_CREDENTIAL_CONFLICT NT_STATUS(0xC0000000 | 0x0195)
#define NT_STATUS_REMOTE_SESSION_LIMIT NT_STATUS(0xC0000000 | 0x0196)
#define NT_STATUS_EVENTLOG_FILE_CHANGED NT_STATUS(0xC0000000 | 0x0197)
#define NT_STATUS_NOLOGON_INTERDOMAIN_TRUST_ACCOUNT NT_STATUS(0xC0000000 | 0x0198)
#define NT_STATUS_NOLOGON_WORKSTATION_TRUST_ACCOUNT NT_STATUS(0xC0000000 | 0x0199)
#define NT_STATUS_NOLOGON_SERVER_TRUST_ACCOUNT NT_STATUS(0xC0000000 | 0x019a)
#define NT_STATUS_DOMAIN_TRUST_INCONSISTENT NT_STATUS(0xC0000000 | 0x019b)
#define NT_STATUS_FS_DRIVER_REQUIRED NT_STATUS(0xC0000000 | 0x019c)
#define NT_STATUS_NO_USER_SESSION_KEY NT_STATUS(0xC0000000 | 0x0202)
#define NT_STATUS_USER_SESSION_DELETED NT_STATUS(0xC0000000 | 0x0203)
#define NT_STATUS_RESOURCE_LANG_NOT_FOUND NT_STATUS(0xC0000000 | 0x0204)
#define NT_STATUS_INSUFF_SERVER_RESOURCES NT_STATUS(0xC0000000 | 0x0205)
#define NT_STATUS_INVALID_BUFFER_SIZE NT_STATUS(0xC0000000 | 0x0206)
#define NT_STATUS_INVALID_ADDRESS_COMPONENT NT_STATUS(0xC0000000 | 0x0207)
#define NT_STATUS_INVALID_ADDRESS_WILDCARD NT_STATUS(0xC0000000 | 0x0208)
#define NT_STATUS_TOO_MANY_ADDRESSES NT_STATUS(0xC0000000 | 0x0209)
#define NT_STATUS_ADDRESS_ALREADY_EXISTS NT_STATUS(0xC0000000 | 0x020a)
#define NT_STATUS_ADDRESS_CLOSED NT_STATUS(0xC0000000 | 0x020b)
#define NT_STATUS_CONNECTION_DISCONNECTED NT_STATUS(0xC0000000 | 0x020c)
#define NT_STATUS_CONNECTION_RESET NT_STATUS(0xC0000000 | 0x020d)
#define NT_STATUS_TOO_MANY_NODES NT_STATUS(0xC0000000 | 0x020e)
#define NT_STATUS_TRANSACTION_ABORTED NT_STATUS(0xC0000000 | 0x020f)
#define NT_STATUS_TRANSACTION_TIMED_OUT NT_STATUS(0xC0000000 | 0x0210)
#define NT_STATUS_TRANSACTION_NO_RELEASE NT_STATUS(0xC0000000 | 0x0211)
#define NT_STATUS_TRANSACTION_NO_MATCH NT_STATUS(0xC0000000 | 0x0212)
#define NT_STATUS_TRANSACTION_RESPONDED NT_STATUS(0xC0000000 | 0x0213)
#define NT_STATUS_TRANSACTION_INVALID_ID NT_STATUS(0xC0000000 | 0x0214)
#define NT_STATUS_TRANSACTION_INVALID_TYPE NT_STATUS(0xC0000000 | 0x0215)
#define NT_STATUS_NOT_SERVER_SESSION NT_STATUS(0xC0000000 | 0x0216)
#define NT_STATUS_NOT_CLIENT_SESSION NT_STATUS(0xC0000000 | 0x0217)
#define NT_STATUS_CANNOT_LOAD_REGISTRY_FILE NT_STATUS(0xC0000000 | 0x0218)
#define NT_STATUS_DEBUG_ATTACH_FAILED NT_STATUS(0xC0000000 | 0x0219)
#define NT_STATUS_SYSTEM_PROCESS_TERMINATED NT_STATUS(0xC0000000 | 0x021a)
#define NT_STATUS_DATA_NOT_ACCEPTED NT_STATUS(0xC0000000 | 0x021b)
#define NT_STATUS_NO_BROWSER_SERVERS_FOUND NT_STATUS(0xC0000000 | 0x021c)
#define NT_STATUS_VDM_HARD_ERROR NT_STATUS(0xC0000000 | 0x021d)
#define NT_STATUS_DRIVER_CANCEL_TIMEOUT NT_STATUS(0xC0000000 | 0x021e)
#define NT_STATUS_REPLY_MESSAGE_MISMATCH NT_STATUS(0xC0000000 | 0x021f)
#define NT_STATUS_MAPPED_ALIGNMENT NT_STATUS(0xC0000000 | 0x0220)
#define NT_STATUS_IMAGE_CHECKSUM_MISMATCH NT_STATUS(0xC0000000 | 0x0221)
#define NT_STATUS_LOST_WRITEBEHIND_DATA NT_STATUS(0xC0000000 | 0x0222)
#define NT_STATUS_CLIENT_SERVER_PARAMETERS_INVALID NT_STATUS(0xC0000000 | 0x0223)
#define NT_STATUS_PASSWORD_MUST_CHANGE NT_STATUS(0xC0000000 | 0x0224)
#define NT_STATUS_NOT_FOUND NT_STATUS(0xC0000000 | 0x0225)
#define NT_STATUS_NOT_TINY_STREAM NT_STATUS(0xC0000000 | 0x0226)
#define NT_STATUS_RECOVERY_FAILURE NT_STATUS(0xC0000000 | 0x0227)
#define NT_STATUS_STACK_OVERFLOW_READ NT_STATUS(0xC0000000 | 0x0228)
#define NT_STATUS_FAIL_CHECK NT_STATUS(0xC0000000 | 0x0229)
#define NT_STATUS_DUPLICATE_OBJECTID NT_STATUS(0xC0000000 | 0x022a)
#define NT_STATUS_OBJECTID_EXISTS NT_STATUS(0xC0000000 | 0x022b)
#define NT_STATUS_CONVERT_TO_LARGE NT_STATUS(0xC0000000 | 0x022c)
#define NT_STATUS_RETRY NT_STATUS(0xC0000000 | 0x022d)
#define NT_STATUS_FOUND_OUT_OF_SCOPE NT_STATUS(0xC0000000 | 0x022e)
#define NT_STATUS_ALLOCATE_BUCKET NT_STATUS(0xC0000000 | 0x022f)
#define NT_STATUS_PROPSET_NOT_FOUND NT_STATUS(0xC0000000 | 0x0230)
#define NT_STATUS_MARSHALL_OVERFLOW NT_STATUS(0xC0000000 | 0x0231)
#define NT_STATUS_INVALID_VARIANT NT_STATUS(0xC0000000 | 0x0232)
#define NT_STATUS_DOMAIN_CONTROLLER_NOT_FOUND NT_STATUS(0xC0000000 | 0x0233)
#define NT_STATUS_ACCOUNT_LOCKED_OUT NT_STATUS(0xC0000000 | 0x0234)
#define NT_STATUS_HANDLE_NOT_CLOSABLE NT_STATUS(0xC0000000 | 0x0235)
#define NT_STATUS_CONNECTION_REFUSED NT_STATUS(0xC0000000 | 0x0236)
#define NT_STATUS_GRACEFUL_DISCONNECT NT_STATUS(0xC0000000 | 0x0237)
#define NT_STATUS_ADDRESS_ALREADY_ASSOCIATED NT_STATUS(0xC0000000 | 0x0238)
#define NT_STATUS_ADDRESS_NOT_ASSOCIATED NT_STATUS(0xC0000000 | 0x0239)
#define NT_STATUS_CONNECTION_INVALID NT_STATUS(0xC0000000 | 0x023a)
#define NT_STATUS_CONNECTION_ACTIVE NT_STATUS(0xC0000000 | 0x023b)
#define NT_STATUS_NETWORK_UNREACHABLE NT_STATUS(0xC0000000 | 0x023c)
#define NT_STATUS_HOST_UNREACHABLE NT_STATUS(0xC0000000 | 0x023d)
#define NT_STATUS_PROTOCOL_UNREACHABLE NT_STATUS(0xC0000000 | 0x023e)
#define NT_STATUS_PORT_UNREACHABLE NT_STATUS(0xC0000000 | 0x023f)
#define NT_STATUS_REQUEST_ABORTED NT_STATUS(0xC0000000 | 0x0240)
#define NT_STATUS_CONNECTION_ABORTED NT_STATUS(0xC0000000 | 0x0241)
#define NT_STATUS_BAD_COMPRESSION_BUFFER NT_STATUS(0xC0000000 | 0x0242)
#define NT_STATUS_USER_MAPPED_FILE NT_STATUS(0xC0000000 | 0x0243)
#define NT_STATUS_AUDIT_FAILED NT_STATUS(0xC0000000 | 0x0244)
#define NT_STATUS_TIMER_RESOLUTION_NOT_SET NT_STATUS(0xC0000000 | 0x0245)
#define NT_STATUS_CONNECTION_COUNT_LIMIT NT_STATUS(0xC0000000 | 0x0246)
#define NT_STATUS_LOGIN_TIME_RESTRICTION NT_STATUS(0xC0000000 | 0x0247)
#define NT_STATUS_LOGIN_WKSTA_RESTRICTION NT_STATUS(0xC0000000 | 0x0248)
#define NT_STATUS_IMAGE_MP_UP_MISMATCH NT_STATUS(0xC0000000 | 0x0249)
#define NT_STATUS_INSUFFICIENT_LOGON_INFO NT_STATUS(0xC0000000 | 0x0250)
#define NT_STATUS_BAD_DLL_ENTRYPOINT NT_STATUS(0xC0000000 | 0x0251)
#define NT_STATUS_BAD_SERVICE_ENTRYPOINT NT_STATUS(0xC0000000 | 0x0252)
#define NT_STATUS_LPC_REPLY_LOST NT_STATUS(0xC0000000 | 0x0253)
#define NT_STATUS_IP_ADDRESS_CONFLICT1 NT_STATUS(0xC0000000 | 0x0254)
#define NT_STATUS_IP_ADDRESS_CONFLICT2 NT_STATUS(0xC0000000 | 0x0255)
#define NT_STATUS_REGISTRY_QUOTA_LIMIT NT_STATUS(0xC0000000 | 0x0256)
#define NT_STATUS_PATH_NOT_COVERED NT_STATUS(0xC0000000 | 0x0257)
#define NT_STATUS_NO_CALLBACK_ACTIVE NT_STATUS(0xC0000000 | 0x0258)
#define NT_STATUS_LICENSE_QUOTA_EXCEEDED NT_STATUS(0xC0000000 | 0x0259)
#define NT_STATUS_PWD_TOO_SHORT NT_STATUS(0xC0000000 | 0x025a)
#define NT_STATUS_PWD_TOO_RECENT NT_STATUS(0xC0000000 | 0x025b)
#define NT_STATUS_PWD_HISTORY_CONFLICT NT_STATUS(0xC0000000 | 0x025c)
#define NT_STATUS_PLUGPLAY_NO_DEVICE NT_STATUS(0xC0000000 | 0x025e)
#define NT_STATUS_UNSUPPORTED_COMPRESSION NT_STATUS(0xC0000000 | 0x025f)
#define NT_STATUS_INVALID_HW_PROFILE NT_STATUS(0xC0000000 | 0x0260)
#define NT_STATUS_INVALID_PLUGPLAY_DEVICE_PATH NT_STATUS(0xC0000000 | 0x0261)
#define NT_STATUS_DRIVER_ORDINAL_NOT_FOUND NT_STATUS(0xC0000000 | 0x0262)
#define NT_STATUS_DRIVER_ENTRYPOINT_NOT_FOUND NT_STATUS(0xC0000000 | 0x0263)
#define NT_STATUS_RESOURCE_NOT_OWNED NT_STATUS(0xC0000000 | 0x0264)
#define NT_STATUS_TOO_MANY_LINKS NT_STATUS(0xC0000000 | 0x0265)
#define NT_STATUS_QUOTA_LIST_INCONSISTENT NT_STATUS(0xC0000000 | 0x0266)
#define NT_STATUS_FILE_IS_OFFLINE NT_STATUS(0xC0000000 | 0x0267)
#define NT_STATUS_NO_SUCH_JOB NT_STATUS(0xC0000000 | 0xEDE) /* scheduler */
/* I use NT_STATUS_FOOBAR when I have no idea what error code to use -
* this means we need a torture test */
#define NT_STATUS_FOOBAR NT_STATUS_UNSUCCESSFUL
#endif /* _NTERR_H */

133
source4/include/ntlmssp.h Normal file
View File

@ -0,0 +1,133 @@
/*
Unix SMB/CIFS implementation.
SMB parameters and setup
Copyright (C) Andrew Tridgell 1992-1997
Copyright (C) Luke Kenneth Casson Leighton 1996-1997
Copyright (C) Paul Ashton 1997
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* NTLMSSP mode */
enum NTLMSSP_ROLE
{
NTLMSSP_SERVER,
NTLMSSP_CLIENT
};
/* NTLMSSP message types */
enum NTLM_MESSAGE_TYPE
{
NTLMSSP_NEGOTIATE = 1,
NTLMSSP_CHALLENGE = 2,
NTLMSSP_AUTH = 3,
NTLMSSP_UNKNOWN = 4
};
/* NTLMSSP negotiation flags */
#define NTLMSSP_NEGOTIATE_UNICODE 0x00000001
#define NTLMSSP_NEGOTIATE_OEM 0x00000002
#define NTLMSSP_REQUEST_TARGET 0x00000004
#define NTLMSSP_NEGOTIATE_SIGN 0x00000010 /* Message integrity */
#define NTLMSSP_NEGOTIATE_SEAL 0x00000020 /* Message confidentiality */
#define NTLMSSP_NEGOTIATE_DATAGRAM_STYLE 0x00000040
#define NTLMSSP_NEGOTIATE_LM_KEY 0x00000080
#define NTLMSSP_NEGOTIATE_NETWARE 0x00000100
#define NTLMSSP_NEGOTIATE_NTLM 0x00000200
#define NTLMSSP_NEGOTIATE_DOMAIN_SUPPLIED 0x00001000
#define NTLMSSP_NEGOTIATE_WORKSTATION_SUPPLIED 0x00002000
#define NTLMSSP_NEGOTIATE_THIS_IS_LOCAL_CALL 0x00004000
#define NTLMSSP_NEGOTIATE_ALWAYS_SIGN 0x00008000
#define NTLMSSP_TARGET_TYPE_DOMAIN 0x10000
#define NTLMSSP_TARGET_TYPE_SERVER 0x20000
#define NTLMSSP_CHAL_INIT_RESPONSE 0x00010000
#define NTLMSSP_CHAL_ACCEPT_RESPONSE 0x00020000
#define NTLMSSP_CHAL_NON_NT_SESSION_KEY 0x00040000
#define NTLMSSP_NEGOTIATE_NTLM2 0x00080000
#define NTLMSSP_CHAL_TARGET_INFO 0x00800000
#define NTLMSSP_NEGOTIATE_128 0x20000000 /* 128-bit encryption */
#define NTLMSSP_NEGOTIATE_KEY_EXCH 0x40000000
#define NTLMSSP_NEGOTIATE_080000000 0x80000000
#define NTLMSSP_NAME_TYPE_DOMAIN 0x01
#define NTLMSSP_NAME_TYPE_SERVER 0x02
#define NTLMSSP_NAME_TYPE_DOMAIN_DNS 0x03
#define NTLMSSP_NAME_TYPE_SERVER_DNS 0x04
typedef struct ntlmssp_state
{
TALLOC_CTX *mem_ctx;
enum NTLMSSP_ROLE role;
BOOL unicode;
char *user;
char *domain;
char *workstation;
DATA_BLOB lm_resp;
DATA_BLOB nt_resp;
DATA_BLOB chal;
void *auth_context;
const uint8 *(*get_challenge)(struct ntlmssp_state *ntlmssp_state);
NTSTATUS (*check_password)(struct ntlmssp_state *ntlmssp_state);
const char *(*get_global_myname)(void);
const char *(*get_domain)(void);
int server_role;
uint32 expected_state;
} NTLMSSP_STATE;
typedef struct ntlmssp_client_state
{
TALLOC_CTX *mem_ctx;
unsigned int ref_count;
BOOL unicode;
BOOL use_ntlmv2;
char *user;
char *domain;
char *workstation;
char *password;
const char *(*get_global_myname)(void);
const char *(*get_domain)(void);
DATA_BLOB chal;
DATA_BLOB lm_resp;
DATA_BLOB nt_resp;
DATA_BLOB session_key;
uint32 neg_flags;
/* SMB Signing */
uint32 ntlmssp_seq_num;
/* ntlmv2 */
char cli_sign_const[16];
char cli_seal_const[16];
char srv_sign_const[16];
char srv_seal_const[16];
unsigned char cli_sign_hash[258];
unsigned char cli_seal_hash[258];
unsigned char srv_sign_hash[258];
unsigned char srv_seal_hash[258];
/* ntlmv1 */
unsigned char ntlmssp_hash[258];
} NTLMSSP_CLIENT_STATE;

86
source4/include/ntvfs.h Normal file
View File

@ -0,0 +1,86 @@
/*
Unix SMB/CIFS implementation.
NTVFS structures and defines
Copyright (C) Andrew Tridgell 2003
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* modules can use the following to determine if the interface has changed */
#define NTVFS_INTERFACE_VERSION 1
/* each backend has to be one one of the following 3 basic types. In
* earlier versions of Samba backends needed to handle all types, now
* we implement them separately. */
enum ntvfs_type {NTVFS_DISK, NTVFS_PRINT, NTVFS_IPC};
/* the ntvfs operations structure - contains function pointers to
the backend implementations of each operation */
struct ntvfs_ops {
/* initial setup */
NTSTATUS (*connect)(struct request_context *req, const char *sharename);
NTSTATUS (*disconnect)(struct tcon_context *conn);
/* path operations */
NTSTATUS (*unlink)(struct request_context *req, struct smb_unlink *unl);
NTSTATUS (*chkpath)(struct request_context *req, struct smb_chkpath *cp);
NTSTATUS (*qpathinfo)(struct request_context *req, union smb_fileinfo *st);
NTSTATUS (*setpathinfo)(struct request_context *req, union smb_setfileinfo *st);
NTSTATUS (*open)(struct request_context *req, union smb_open *oi);
NTSTATUS (*mkdir)(struct request_context *req, union smb_mkdir *md);
NTSTATUS (*rmdir)(struct request_context *req, struct smb_rmdir *rd);
NTSTATUS (*rename)(struct request_context *req, struct smb_rename *ren);
NTSTATUS (*copy)(struct request_context *req, struct smb_copy *cp);
/* directory search */
NTSTATUS (*search_first)(struct request_context *req, union smb_search_first *io, void *private,
BOOL (*callback)(void *private, union smb_search_data *file));
NTSTATUS (*search_next)(struct request_context *req, union smb_search_next *io, void *private,
BOOL (*callback)(void *private, union smb_search_data *file));
NTSTATUS (*search_close)(struct request_context *req, union smb_search_close *io);
/* operations on open files */
NTSTATUS (*ioctl)(struct request_context *req, struct smb_ioctl *io);
NTSTATUS (*read)(struct request_context *req, union smb_read *io);
NTSTATUS (*write)(struct request_context *req, union smb_write *io);
NTSTATUS (*seek)(struct request_context *req, struct smb_seek *io);
NTSTATUS (*flush)(struct request_context *req, struct smb_flush *flush);
NTSTATUS (*close)(struct request_context *req, union smb_close *io);
NTSTATUS (*exit)(struct request_context *req);
NTSTATUS (*lock)(struct request_context *req, union smb_lock *lck);
NTSTATUS (*setfileinfo)(struct request_context *req, union smb_setfileinfo *info);
NTSTATUS (*qfileinfo)(struct request_context *req, union smb_fileinfo *info);
/* filesystem operations */
NTSTATUS (*fsinfo)(struct request_context *req, union smb_fsinfo *fs);
/* printing specific operations */
NTSTATUS (*lpq)(struct request_context *req, union smb_lpq *lpq);
/* trans interfaces - only used by CIFS backend to prover complete passthru for testing */
NTSTATUS (*trans2)(struct request_context *req, struct smb_trans2 *trans2);
};
/* this structure is used by backends to determine the size of some critical types */
struct ntvfs_critical_sizes {
int sizeof_ntvfs_ops;
int sizeof_SMB_OFF_T;
int sizeof_tcon_context;
int sizeof_request_context;
};

155
source4/include/passdb.h Normal file
View File

@ -0,0 +1,155 @@
/*
Unix SMB/CIFS implementation.
passdb structures and parameters
Copyright (C) Gerald Carter 2001
Copyright (C) Luke Kenneth Casson Leighton 1998 - 2000
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _PASSDB_H
#define _PASSDB_H
/*****************************************************************
Functions to be implemented by the new (v2) passdb API
****************************************************************/
/*
* This next constant specifies the version number of the PASSDB interface
* this SAMBA will load. Increment this if *ANY* changes are made to the interface.
*/
#define PASSDB_INTERFACE_VERSION 4
typedef struct pdb_context
{
struct pdb_methods *pdb_methods;
struct pdb_methods *pwent_methods;
/* These functions are wrappers for the functions listed above.
They may do extra things like re-reading a SAM_ACCOUNT on update */
NTSTATUS (*pdb_setsampwent)(struct pdb_context *, BOOL update);
void (*pdb_endsampwent)(struct pdb_context *);
NTSTATUS (*pdb_getsampwent)(struct pdb_context *, SAM_ACCOUNT *user);
NTSTATUS (*pdb_getsampwnam)(struct pdb_context *, SAM_ACCOUNT *sam_acct, const char *username);
NTSTATUS (*pdb_getsampwsid)(struct pdb_context *, SAM_ACCOUNT *sam_acct, const DOM_SID *sid);
NTSTATUS (*pdb_add_sam_account)(struct pdb_context *, SAM_ACCOUNT *sampass);
NTSTATUS (*pdb_update_sam_account)(struct pdb_context *, SAM_ACCOUNT *sampass);
NTSTATUS (*pdb_delete_sam_account)(struct pdb_context *, SAM_ACCOUNT *username);
NTSTATUS (*pdb_getgrsid)(struct pdb_context *context, GROUP_MAP *map,
DOM_SID sid, BOOL with_priv);
NTSTATUS (*pdb_getgrgid)(struct pdb_context *context, GROUP_MAP *map,
gid_t gid, BOOL with_priv);
NTSTATUS (*pdb_getgrnam)(struct pdb_context *context, GROUP_MAP *map,
char *name, BOOL with_priv);
NTSTATUS (*pdb_add_group_mapping_entry)(struct pdb_context *context,
GROUP_MAP *map);
NTSTATUS (*pdb_update_group_mapping_entry)(struct pdb_context *context,
GROUP_MAP *map);
NTSTATUS (*pdb_delete_group_mapping_entry)(struct pdb_context *context,
DOM_SID sid);
NTSTATUS (*pdb_enum_group_mapping)(struct pdb_context *context,
enum SID_NAME_USE sid_name_use,
GROUP_MAP **rmap, int *num_entries,
BOOL unix_only, BOOL with_priv);
void (*free_fn)(struct pdb_context **);
TALLOC_CTX *mem_ctx;
} PDB_CONTEXT;
typedef struct pdb_methods
{
const char *name; /* What name got this module */
struct pdb_context *parent;
/* Use macros from dlinklist.h on these two */
struct pdb_methods *next;
struct pdb_methods *prev;
NTSTATUS (*setsampwent)(struct pdb_methods *, BOOL update);
void (*endsampwent)(struct pdb_methods *);
NTSTATUS (*getsampwent)(struct pdb_methods *, SAM_ACCOUNT *user);
NTSTATUS (*getsampwnam)(struct pdb_methods *, SAM_ACCOUNT *sam_acct, const char *username);
NTSTATUS (*getsampwsid)(struct pdb_methods *, SAM_ACCOUNT *sam_acct, const DOM_SID *Sid);
NTSTATUS (*add_sam_account)(struct pdb_methods *, SAM_ACCOUNT *sampass);
NTSTATUS (*update_sam_account)(struct pdb_methods *, SAM_ACCOUNT *sampass);
NTSTATUS (*delete_sam_account)(struct pdb_methods *, SAM_ACCOUNT *username);
NTSTATUS (*getgrsid)(struct pdb_methods *methods, GROUP_MAP *map,
DOM_SID sid, BOOL with_priv);
NTSTATUS (*getgrgid)(struct pdb_methods *methods, GROUP_MAP *map,
gid_t gid, BOOL with_priv);
NTSTATUS (*getgrnam)(struct pdb_methods *methods, GROUP_MAP *map,
char *name, BOOL with_priv);
NTSTATUS (*add_group_mapping_entry)(struct pdb_methods *methods,
GROUP_MAP *map);
NTSTATUS (*update_group_mapping_entry)(struct pdb_methods *methods,
GROUP_MAP *map);
NTSTATUS (*delete_group_mapping_entry)(struct pdb_methods *methods,
DOM_SID sid);
NTSTATUS (*enum_group_mapping)(struct pdb_methods *methods,
enum SID_NAME_USE sid_name_use,
GROUP_MAP **rmap, int *num_entries,
BOOL unix_only, BOOL with_priv);
void *private_data; /* Private data of some kind */
void (*free_private_data)(void **);
} PDB_METHODS;
typedef NTSTATUS (*pdb_init_function)(struct pdb_context *,
struct pdb_methods **,
const char *);
struct pdb_init_function_entry {
const char *name;
/* Function to create a member of the pdb_methods list */
pdb_init_function init;
struct pdb_init_function_entry *prev, *next;
};
#endif /* _PASSDB_H */

View File

@ -0,0 +1,48 @@
/*
Unix SMB/CIFS implementation.
Common popt arguments
Copyright (C) Jelmer Vernooij 2003
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _POPT_COMMON_H
#define _POPT_COMMON_H
/* Common popt structures */
extern struct poptOption popt_common_samba[];
extern struct poptOption popt_common_connection[];
extern struct poptOption popt_common_version[];
extern struct poptOption popt_common_credentials[];
#ifndef POPT_TABLEEND
#define POPT_TABLEEND { NULL, '\0', 0, 0, 0, NULL, NULL }
#endif
#define POPT_COMMON_SAMBA { NULL, 0, POPT_ARG_INCLUDE_TABLE, popt_common_samba, 0, "Common samba options:", NULL },
#define POPT_COMMON_CONNECTION { NULL, 0, POPT_ARG_INCLUDE_TABLE, popt_common_connection, 0, "Connection options:", NULL },
#define POPT_COMMON_VERSION { NULL, 0, POPT_ARG_INCLUDE_TABLE, popt_common_version, 0, "Common samba options:", NULL },
#define POPT_COMMON_CREDENTIALS { NULL, 0, POPT_ARG_INCLUDE_TABLE, popt_common_credentials, 0, "Authentication options:", NULL },
struct user_auth_info {
pstring username;
pstring password;
BOOL got_pass;
BOOL use_kerberos;
};
extern struct user_auth_info cmdline_auth_info;
#endif /* _POPT_COMMON_H */

102
source4/include/printing.h Normal file
View File

@ -0,0 +1,102 @@
#ifndef PRINTING_H_
#define PRINTING_H_
/*
Unix SMB/CIFS implementation.
printing definitions
Copyright (C) Andrew Tridgell 1992-2000
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#include "includes.h"
/*
This file defines the low-level printing system interfaces used by the
SAMBA printing subsystem.
*/
/* Information for print jobs */
struct printjob {
pid_t pid; /* which process launched the job */
int sysjob; /* the system (lp) job number */
int fd; /* file descriptor of open file if open */
time_t starttime; /* when the job started spooling */
int status; /* the status of this job */
size_t size; /* the size of the job so far */
int page_count; /* then number of pages so far */
BOOL spooled; /* has it been sent to the spooler yet? */
BOOL smbjob; /* set if the job is a SMB job */
fstring filename; /* the filename used to spool the file */
fstring jobname; /* the job name given to us by the client */
fstring user; /* the user who started the job */
fstring queuename; /* service number of printer for this job */
NT_DEVICEMODE *nt_devmode;
};
/* Information for print interfaces */
struct printif
{
int (*queue_get)(int snum, print_queue_struct **q,
print_status_struct *status);
int (*queue_pause)(int snum);
int (*queue_resume)(int snum);
int (*job_delete)(int snum, struct printjob *pjob);
int (*job_pause)(int snum, struct printjob *pjob);
int (*job_resume)(int snum, struct printjob *pjob);
int (*job_submit)(int snum, struct printjob *pjob);
};
extern struct printif generic_printif;
#ifdef HAVE_CUPS
extern struct printif cups_printif;
#endif /* HAVE_CUPS */
/* PRINT_MAX_JOBID is now defined in local.h */
#define UNIX_JOB_START PRINT_MAX_JOBID
#define NEXT_JOBID(j) ((j+1) % PRINT_MAX_JOBID > 0 ? (j+1) % PRINT_MAX_JOBID : 1)
#define MAX_CACHE_VALID_TIME 3600
#define PRINT_SPOOL_PREFIX "smbprn."
#define PRINT_DATABASE_VERSION 5
/* There can be this many printing tdb's open, plus any locked ones. */
#define MAX_PRINT_DBS_OPEN 1
struct tdb_print_db {
struct tdb_print_db *next, *prev;
TDB_CONTEXT *tdb;
int ref_count;
fstring printer_name;
};
/*
* Used for print notify
*/
#define NOTIFY_PID_LIST_KEY "NOTIFY_PID_LIST"
struct notify_queue {
struct notify_queue *next, *prev;
struct spoolss_notify_msg *msg;
char *buf;
size_t buflen;
};
#endif /* PRINTING_H_ */

View File

@ -0,0 +1,49 @@
/*
Unix SMB/CIFS implementation.
process model structures and defines
Copyright (C) Andrew Tridgell 2003
Copyright (C) James J Myers 2003 <myersjj@samba.org>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
/* modules can use the following to determine if the interface has changed */
#define MODEL_INTERFACE_VERSION 1
/* the process model operations structure - contains function pointers to
the model-specific implementations of each operation */
struct model_ops {
/* setup handler functions for select */
void (*setup_handlers)(struct smbd_context *smbd, struct socket_select *socket_sel);
/* function to reload services if necessary */
void (*check_sighup)(struct smbd_context *smbd);
/* function to accept new connection */
BOOL (*accept_connection)(struct smbd_context *smbd, void **private,
int fd, enum socket_state *state);
/* function to terminate a connection */
void (*terminate_connection)( struct server_context *smb, const char *reason);
/* function to exit server */
void (*exit_server)(struct server_context *smb, const char *reason);
/* synchronization operations */
int (*mutex_init) (pthread_mutex_t *mutex, const pthread_mutexattr_t *mutex_attr);
int (*mutex_lock) (pthread_mutex_t *mutex);
int (*mutex_unlock) (pthread_mutex_t *mutex);
int (*mutex_destroy) (pthread_mutex_t *mutex);
};

36
source4/include/pstring.h Normal file
View File

@ -0,0 +1,36 @@
/*
samba -- Unix SMB/CIFS implementation.
Safe standardized string types
Copyright (C) Andrew Tridgell 1992-2000
Copyright (C) John H Terpstra 1996-2000
Copyright (C) Luke Kenneth Casson Leighton 1996-2000
Copyright (C) Paul Ashton 1998-2000
Copyright (C) Martin Pool 2002
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _PSTRING
#define PSTRING_LEN 1024
#define FSTRING_LEN 256
typedef char pstring[PSTRING_LEN];
typedef char fstring[FSTRING_LEN];
#define _PSTRING
#endif /* ndef _PSTRING */

507
source4/include/rap.h Executable file
View File

@ -0,0 +1,507 @@
/*
Samba Unix/Linux SMB client library
RAP (SMB Remote Procedure Calls) defines and structures
Copyright (C) Steve French 2001 (sfrench@us.ibm.com)
Copyright (C) Jim McDonough 2001 (jmcd@us.ibm.com)
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _RAP_H_
#define _RAP_H_
/*****************************************************/
/* */
/* Additional RAP functionality */
/* */
/* RAP is the original SMB RPC, documented */
/* by Microsoft and X/Open in the 1990s and */
/* supported by most SMB/CIFS servers although */
/* it is unlikely that any one implementation */
/* supports all RAP command codes since some */
/* are quite obsolete and a few are specific */
/* to a particular network operating system */
/* */
/* Although it has largely been replaced */
/* for complex remote admistration and management */
/* (of servers) by the relatively newer */
/* DCE/RPC based remote API (which better handles */
/* large >64K data structures), there are many */
/* important administrative and resource location */
/* tasks and user tasks (e.g. password change) */
/* that are performed via RAP. */
/* */
/* Although a few of the RAP calls are implemented */
/* in the Samba client library already (clirap.c) */
/* the new ones are in clirap2.c for easy patching */
/* and integration and a corresponding header */
/* file, rap.h, has been created. */
/* */
/* This is based on data from the CIFS spec */
/* and the LAN Server and LAN Manager */
/* Programming Reference books and published */
/* RAP document and CIFS forum postings and */
/* lots of trial and error. Additional */
/* background information is available from the */
/* X/Open reference book in their PC Interworking */
/* series "IPC for SMB" and also from the */
/* interoperability documentation in */
/* ftp://ftp.microsoft.com/developr/drg/cifs */
/* */
/* Function names changed from API_ (as they are */
/* in the CIFS specification to RAP_ in order */
/* to avoid confusion with other API calls */
/* sent via DCE RPC */
/* */
/*****************************************************/
/*****************************************************/
/* */
/* Although without pound defines (of this header) */
/* cifsrap.c already includes support for: */
/* */
/* WshareEnum (API number 0, level 1) */
/* NetServerEnum2 (API num 104, level 1) */
/* WWkstaUserLogon (132) */
/* SamOEMchgPasswordUser2_P (214) */
/* */
/* and cifsprint.c already includes support for: */
/* */
/* WPrintJobEnum (API num 76, level 2) */
/* WPrintJobDel (API num 81) */
/* */
/*****************************************************/
#define RAP_WshareEnum 0
#define RAP_WshareGetInfo 1
#define RAP_WshareSetInfo 2
#define RAP_WshareAdd 3
#define RAP_WshareDel 4
#define RAP_NetShareCheck 5
#define RAP_WsessionEnum 6
#define RAP_WsessionGetInfo 7
#define RAP_WsessionDel 8
#define RAP_WconnectionEnum 9
#define RAP_WfileEnum 10
#define RAP_WfileGetInfo 11
#define RAP_WfileClose 12
#define RAP_WserverGetInfo 13
#define RAP_WserverSetInfo 14
#define RAP_WserverDiskEnum 15
#define RAP_WserverAdminCommand 16
#define RAP_NetAuditOpen 17
#define RAP_WauditClear 18
#define RAP_NetErrorLogOpen 19
#define RAP_WerrorLogClear 20
#define RAP_NetCharDevEnum 21
#define RAP_NetCharDevGetInfo 22
#define RAP_WCharDevControl 23
#define RAP_NetCharDevQEnum 24
#define RAP_NetCharDevQGetInfo 25
#define RAP_WCharDevQSetInfo 26
#define RAP_WCharDevQPurge 27
#define RAP_WCharDevQPurgeSelf 28
#define RAP_WMessageNameEnum 29
#define RAP_WMessageNameGetInfo 30
#define RAP_WMessageNameAdd 31
#define RAP_WMessageNameDel 32
#define RAP_WMessageNameFwd 33
#define RAP_WMessageNameUnFwd 34
#define RAP_WMessageBufferSend 35
#define RAP_WMessageFileSend 36
#define RAP_WMessageLogFileSet 37
#define RAP_WMessageLogFileGet 38
#define RAP_WServiceEnum 39
#define RAP_WServiceInstall 40
#define RAP_WServiceControl 41
#define RAP_WAccessEnum 42
#define RAP_WAccessGetInfo 43
#define RAP_WAccessSetInfo 44
#define RAP_WAccessAdd 45
#define RAP_WAccessDel 46
#define RAP_WGroupEnum 47
#define RAP_WGroupAdd 48
#define RAP_WGroupDel 49
#define RAP_WGroupAddUser 50
#define RAP_WGroupDelUser 51
#define RAP_WGroupGetUsers 52
#define RAP_WUserEnum 53
#define RAP_WUserAdd 54
#define RAP_WUserDel 55
#define RAP_WUserGetInfo 56
#define RAP_WUserSetInfo 57
#define RAP_WUserPasswordSet 58
#define RAP_WUserGetGroups 59
#define RAP_WWkstaSetUID 62
#define RAP_WWkstaGetInfo 63
#define RAP_WWkstaSetInfo 64
#define RAP_WUseEnum 65
#define RAP_WUseAdd 66
#define RAP_WUseDel 67
#define RAP_WUseGetInfo 68
#define RAP_WPrintQEnum 69
#define RAP_WPrintQGetInfo 70
#define RAP_WPrintQSetInfo 71
#define RAP_WPrintQAdd 72
#define RAP_WPrintQDel 73
#define RAP_WPrintQPause 74
#define RAP_WPrintQContinue 75
#define RAP_WPrintJobEnum 76
#define RAP_WPrintJobGetInfo 77
#define RAP_WPrintJobSetInfo_OLD 78
#define RAP_WPrintJobDel 81
#define RAP_WPrintJobPause 82
#define RAP_WPrintJobContinue 83
#define RAP_WPrintDestEnum 84
#define RAP_WPrintDestGetInfo 85
#define RAP_WPrintDestControl 86
#define RAP_WProfileSave 87
#define RAP_WProfileLoad 88
#define RAP_WStatisticsGet 89
#define RAP_WStatisticsClear 90
#define RAP_NetRemoteTOD 91
#define RAP_WNetBiosEnum 92
#define RAP_WNetBiosGetInfo 93
#define RAP_NetServerEnum 94
#define RAP_I_NetServerEnum 95
#define RAP_WServiceGetInfo 96
#define RAP_WPrintQPurge 103
#define RAP_NetServerEnum2 104
#define RAP_WAccessGetUserPerms 105
#define RAP_WGroupGetInfo 106
#define RAP_WGroupSetInfo 107
#define RAP_WGroupSetUsers 108
#define RAP_WUserSetGroups 109
#define RAP_WUserModalsGet 110
#define RAP_WUserModalsSet 111
#define RAP_WFileEnum2 112
#define RAP_WUserAdd2 113
#define RAP_WUserSetInfo2 114
#define RAP_WUserPasswordSet2 115
#define RAP_I_NetServerEnum2 116
#define RAP_WConfigGet2 117
#define RAP_WConfigGetAll2 118
#define RAP_WGetDCName 119
#define RAP_NetHandleGetInfo 120
#define RAP_NetHandleSetInfo 121
#define RAP_WStatisticsGet2 122
#define RAP_WBuildGetInfo 123
#define RAP_WFileGetInfo2 124
#define RAP_WFileClose2 125
#define RAP_WNetServerReqChallenge 126
#define RAP_WNetServerAuthenticate 127
#define RAP_WNetServerPasswordSet 128
#define RAP_WNetAccountDeltas 129
#define RAP_WNetAccountSync 130
#define RAP_WUserEnum2 131
#define RAP_WWkstaUserLogon 132
#define RAP_WWkstaUserLogoff 133
#define RAP_WLogonEnum 134
#define RAP_WErrorLogRead 135
#define RAP_NetPathType 136
#define RAP_NetPathCanonicalize 137
#define RAP_NetPathCompare 138
#define RAP_NetNameValidate 139
#define RAP_NetNameCanonicalize 140
#define RAP_NetNameCompare 141
#define RAP_WAuditRead 142
#define RAP_WPrintDestAdd 143
#define RAP_WPrintDestSetInfo 144
#define RAP_WPrintDestDel 145
#define RAP_WUserValidate2 146
#define RAP_WPrintJobSetInfo 147
#define RAP_TI_NetServerDiskEnum 148
#define RAP_TI_NetServerDiskGetInfo 149
#define RAP_TI_FTVerifyMirror 150
#define RAP_TI_FTAbortVerify 151
#define RAP_TI_FTGetInfo 152
#define RAP_TI_FTSetInfo 153
#define RAP_TI_FTLockDisk 154
#define RAP_TI_FTFixError 155
#define RAP_TI_FTAbortFix 156
#define RAP_TI_FTDiagnoseError 157
#define RAP_TI_FTGetDriveStats 158
#define RAP_TI_FTErrorGetInfo 160
#define RAP_NetAccessCheck 163
#define RAP_NetAlertRaise 164
#define RAP_NetAlertStart 165
#define RAP_NetAlertStop 166
#define RAP_NetAuditWrite 167
#define RAP_NetIRemoteAPI 168
#define RAP_NetServiceStatus 169
#define RAP_NetServerRegister 170
#define RAP_NetServerDeregister 171
#define RAP_NetSessionEntryMake 172
#define RAP_NetSessionEntryClear 173
#define RAP_NetSessionEntryGetInfo 174
#define RAP_NetSessionEntrySetInfo 175
#define RAP_NetConnectionEntryMake 176
#define RAP_NetConnectionEntryClear 177
#define RAP_NetConnectionEntrySetInfo 178
#define RAP_NetConnectionEntryGetInfo 179
#define RAP_NetFileEntryMake 180
#define RAP_NetFileEntryClear 181
#define RAP_NetFileEntrySetInfo 182
#define RAP_NetFileEntryGetInfo 183
#define RAP_AltSrvMessageBufferSend 184
#define RAP_AltSrvMessageFileSend 185
#define RAP_wI_NetRplWkstaEnum 186
#define RAP_wI_NetRplWkstaGetInfo 187
#define RAP_wI_NetRplWkstaSetInfo 188
#define RAP_wI_NetRplWkstaAdd 189
#define RAP_wI_NetRplWkstaDel 190
#define RAP_wI_NetRplProfileEnum 191
#define RAP_wI_NetRplProfileGetInfo 192
#define RAP_wI_NetRplProfileSetInfo 193
#define RAP_wI_NetRplProfileAdd 194
#define RAP_wI_NetRplProfileDel 195
#define RAP_wI_NetRplProfileClone 196
#define RAP_wI_NetRplBaseProfileEnum 197
#define RAP_WIServerSetInfo 201
#define RAP_WPrintDriverEnum 205
#define RAP_WPrintQProcessorEnum 206
#define RAP_WPrintPortEnum 207
#define RAP_WNetWriteUpdateLog 208
#define RAP_WNetAccountUpdate 209
#define RAP_WNetAccountConfirmUpdate 210
#define RAP_WConfigSet 211
#define RAP_WAccountsReplicate 212
#define RAP_SamOEMChgPasswordUser2_P 214
#define RAP_NetServerEnum3 215
#define RAP_WprintDriverGetInfo 250
#define RAP_WprintDriverSetInfo 251
#define RAP_WaliasAdd 252
#define RAP_WaliasDel 253
#define RAP_WaliasGetInfo 254
#define RAP_WaliasSetInfo 255
#define RAP_WaliasEnum 256
#define RAP_WuserGetLogonAsn 257
#define RAP_WuserSetLogonAsn 258
#define RAP_WuserGetAppSel 259
#define RAP_WuserSetAppSel 260
#define RAP_WappAdd 261
#define RAP_WappDel 262
#define RAP_WappGetInfo 263
#define RAP_WappSetInfo 264
#define RAP_WappEnum 265
#define RAP_WUserDCDBInit 266
#define RAP_WDASDAdd 267
#define RAP_WDASDDel 268
#define RAP_WDASDGetInfo 269
#define RAP_WDASDSetInfo 270
#define RAP_WDASDEnum 271
#define RAP_WDASDCheck 272
#define RAP_WDASDCtl 273
#define RAP_WuserRemoteLogonCheck 274
#define RAP_WUserPasswordSet3 275
#define RAP_WCreateRIPLMachine 276
#define RAP_WDeleteRIPLMachine 277
#define RAP_WGetRIPLMachineInfo 278
#define RAP_WSetRIPLMachineInfo 279
#define RAP_WEnumRIPLMachine 280
#define RAP_I_ShareAdd 281
#define RAP_AliasEnum 282
#define RAP_WaccessApply 283
#define RAP_WPrt16Query 284
#define RAP_WPrt16Set 285
#define RAP_WUserDel100 286
#define RAP_WUserRemoteLogonCheck2 287
#define RAP_WRemoteTODSet 294
#define RAP_WprintJobMoveAll 295
#define RAP_W16AppParmAdd 296
#define RAP_W16AppParmDel 297
#define RAP_W16AppParmGet 298
#define RAP_W16AppParmSet 299
#define RAP_W16RIPLMachineCreate 300
#define RAP_W16RIPLMachineGetInfo 301
#define RAP_W16RIPLMachineSetInfo 302
#define RAP_W16RIPLMachineEnum 303
#define RAP_W16RIPLMachineListParmEnum 304
#define RAP_W16RIPLMachClassGetInfo 305
#define RAP_W16RIPLMachClassEnum 306
#define RAP_W16RIPLMachClassCreate 307
#define RAP_W16RIPLMachClassSetInfo 308
#define RAP_W16RIPLMachClassDelete 309
#define RAP_W16RIPLMachClassLPEnum 310
#define RAP_W16RIPLMachineDelete 311
#define RAP_W16WSLevelGetInfo 312
#define RAP_WserverNameAdd 313
#define RAP_WserverNameDel 314
#define RAP_WserverNameEnum 315
#define RAP_I_WDASDEnum 316
#define RAP_WDASDEnumTerminate 317
#define RAP_WDASDSetInfo2 318
#define MAX_API 318
/* Parameter description strings for RAP calls */
/* Names are defined name for RAP call with _REQ */
/* appended to end. */
#define RAP_WFileEnum2_REQ "zzWrLehb8g8"
#define RAP_WFileGetInfo2_REQ "DWrLh"
#define RAP_WFileClose2_REQ "D"
#define RAP_NetGroupEnum_REQ "WrLeh"
#define RAP_NetGroupAdd_REQ "WsT"
#define RAP_NetGroupDel_REQ "z"
#define RAP_NetGroupAddUser_REQ "zz"
#define RAP_NetGroupDelUser_REQ "zz"
#define RAP_NetGroupGetUsers_REQ "zWrLeh"
#define RAP_NetGroupSetUsers_REQ "zWsTW"
#define RAP_NetUserAdd2_REQ "WsTWW"
#define RAP_NetUserEnum_REQ "WrLeh"
#define RAP_NetUserEnum2_REQ "WrLDieh"
#define RAP_NetUserGetGroups_REQ "zWrLeh"
#define RAP_NetUserSetGroups_REQ "zWsTW"
#define RAP_NetUserPasswordSet_REQ "zb16b16w"
#define RAP_NetUserPasswordSet2_REQ "zb16b16WW"
#define RAP_SAMOEMChgPasswordUser2_REQ "B516B16"
#define RAP_NetUserValidate2_REQ "Wb62WWrLhWW"
#define RAP_NetServerEnum2_REQ "WrLehDz"
#define RAP_WserverGetInfo_REQ "WrLh"
#define RAP_NetWkstatGetInfo "WrLh"
#define RAP_WShareAdd_REQ "WsT"
#define RAP_WShareEnum_REQ "WrLeh"
#define RAP_WShareDel_REQ "zW"
#define RAP_WWkstaGetInfo_REQ "WrLh"
#define RAP_NetPrintQEnum_REQ "WrLeh"
#define RAP_NetPrintQGetInfo_REQ "zWrLh"
#define RAP_NetServerAdminCommand_REQ "zhrLeh"
#define RAP_NetServiceEnum_REQ "WrLeh"
#define RAP_NetServiceControl_REQ "zWWrL"
#define RAP_NetServiceInstall_REQ "zF88sg88T"
#define RAP_NetServiceGetInfo_REQ "zWrLh"
#define RAP_NetSessionEnum_REQ "WrLeh"
#define RAP_NetSessionGetInfo_REQ "zWrLh"
#define RAP_NetSessionDel_REQ "zW"
#define RAP_NetConnectionEnum_REQ "zWrLeh"
#define RAP_NetWkstaUserLogoff_REQ "zzWb38WrLh"
/* Description strings for returned data in RAP calls */
/* I use all caps here in part to avoid accidental */
/* name collisions */
#define RAP_FILE_INFO_L2 "D"
#define RAP_FILE_INFO_L3 "DWWzz"
#define RAP_GROUP_INFO_L0 "B21"
#define RAP_GROUP_INFO_L1 "B21Bz"
#define RAP_GROUP_USERS_INFO_0 "B21"
#define RAP_GROUP_USERS_INFO_1 "B21BN"
#define RAP_USER_INFO_L0 "B21"
#define RAP_USER_INFO_L1 "B21BB16DWzzWz"
#define RAP_SERVER_INFO_L0 "B16"
#define RAP_SERVER_INFO_L1 "B16BBDz"
#define RAP_SERVER_INFO_L2 "B16BBDzDDDWWzWWWWWWWB21BzWWWWWWWWWWWWWWWWWWWWWWz"
#define RAP_SERVER_INFO_L3 "B16BBDzDDDWWzWWWWWWWB21BzWWWWWWWWWWWWWWWWWWWWWWzDWz"
#define RAP_SERVICE_INFO_L0 "B16"
#define RAP_SERVICE_INFO_L2 "B16WDWB64"
#define RAP_SHARE_INFO_L0 "B13"
#define RAP_SHARE_INFO_L1 "B13BWz"
#define RAP_SHARE_INFO_L2 "B13BWzWWWzB9B"
#define RAP_PRINTQ_INFO_L2 "B13BWWWzzzzzWN"
#define RAP_SMB_PRINT_JOB_L1 "WB21BB16B10zWWzDDz"
#define RAP_SESSION_INFO_L2 "zzWWWDDDz"
#define RAP_CONNECTION_INFO_L1 "WWWWDzz"
#define RAP_USER_LOGOFF_INFO_L1 "WDW"
#define RAP_WKSTA_INFO_L1 "WDzzzzBBDWDWWWWWWWWWWWWWWWWWWWzzWzzW"
#define RAP_WKSTA_INFO_L10 "zzzBBzz"
/* BB explicit packing would help in structs below */
/* sizes of fixed-length fields, including null terminator */
#define RAP_GROUPNAME_LEN 21
#define RAP_USERNAME_LEN 21
#define RAP_SHARENAME_LEN 13
#define RAP_UPASSWD_LEN 16 /* user password */
#define RAP_SPASSWD_LEN 9 /* share password */
#define RAP_MACHNAME_LEN 16
#define RAP_SRVCNAME_LEN 16
#define RAP_SRVCCMNT_LEN 64
#define RAP_DATATYPE_LEN 10
typedef struct rap_group_info_1
{
char group_name[RAP_GROUPNAME_LEN];
char reserved1;
char * comment;
} RAP_GROUP_INFO_1;
typedef struct rap_user_info_1
{
char user_name[RAP_USERNAME_LEN];
char reserved1;
char passwrd[RAP_UPASSWD_LEN];
uint32 pwage;
uint16 priv;
char * home_dir;
char * comment;
uint16 userflags;
char * logon_script;
} RAP_USER_INFO_1;
typedef struct rap_service_info_2
{
char service_name[RAP_SRVCNAME_LEN];
uint16 status;
uint32 installcode;
uint16 process_num;
char * comment;
} RAP_SERVICE_INFO_2;
typedef struct rap_share_info_0
{
char share_name[RAP_SHARENAME_LEN];
} RAP_SHARE_INFO_0;
typedef struct rap_share_info_1
{
char share_name[RAP_SHARENAME_LEN];
char reserved1;
uint16 share_type;
char * comment;
} RAP_SHARE_INFO_1;
typedef struct rap_share_info_2
{
char share_name[RAP_SHARENAME_LEN];
char reserved1;
uint16 share_type;
char * comment;
uint16 perms;
uint16 maximum_users;
uint16 active_users;
char * path;
char password[RAP_SPASSWD_LEN];
char reserved2;
} RAP_SHARE_INFO_2;
#endif /* _RAP_H_ */

80
source4/include/rpc_brs.h Normal file
View File

@ -0,0 +1,80 @@
/*
Unix SMB/CIFS implementation.
SMB parameters and setup
Copyright (C) Andrew Tridgell 1992-1999
Copyright (C) Luke Kenneth Casson Leighton 1996-1999
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _RPC_BRS_H /* _RPC_BRS_H */
#define _RPC_BRS_H
/* brssvc pipe */
#define BRS_QUERY_INFO 0x02
/* BRS_Q_QUERY_INFO - probably a capabilities request */
typedef struct q_brs_query_info_info
{
uint32 ptr_srv_name; /* pointer (to server name?) */
UNISTR2 uni_srv_name; /* unicode server name starting with '\\' */
uint16 switch_value1; /* info level 100 (0x64) */
/* align */
uint16 switch_value2; /* info level 100 (0x64) */
uint32 ptr;
uint32 pad1;
uint32 pad2;
} BRS_Q_QUERY_INFO;
/* BRS_INFO_100 - level 100 info */
typedef struct brs_info_100_info
{
uint32 pad1;
uint32 ptr2;
uint32 pad2;
uint32 pad3;
} BRS_INFO_100;
/* BRS_R_QUERY_INFO - probably a capabilities request */
typedef struct r_brs_query_info_info
{
uint16 switch_value1; /* 100 (0x64) - switch value */
/* align */
uint16 switch_value2; /* info level 100 (0x64) */
/* for now, only level 100 is supported. this should be an enum container */
uint32 ptr_1; /* pointer 1 */
union
{
BRS_INFO_100 *brs100; /* browser info level 100 */
void *id;
} info;
NTSTATUS status; /* return status */
} BRS_R_QUERY_INFO;
#endif /* _RPC_BRS_H */

View File

@ -0,0 +1,28 @@
/*
Unix SMB/CIFS implementation.
SMB parameters and setup
Copyright (C) Elrond 2000
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
*/
#ifndef _RPC_CLIENT_H
#define _RPC_CLIENT_H
#if 0 /* JERRY */
#include "rpc_client_proto.h"
#endif
#endif /* _RPC_CLIENT_H */

Some files were not shown because too many files have changed in this diff Show More