+Changes in 3.1.0
+================
+* NEW: AFP Spotlight support with Gnome Tracker
+* NEW: New option "spotlight" (G/V)
+* NEW: Configure option --with-tracker-pkgconfig-version
+* NEW: Configure option --with-tracker-prefix
+* NEW: If Spotlight is enabled, launch our own dbus instance
+* NEW: New option "dbus daemon" (G)
+* UPD: Add configure option --with-afpstats for overriding the
+ result of autodetecting dbus-glib presence
+
Changes in 3.0.6
================
* FIX: charset conversion failed when copying from Mac OS 9. Bug #523.
* NEW: Add support for ZFS ACLs on FreeBSD with libsunacl. From FR#83.
* FIX: Active Directory LDAP queries for ACL support with new options
"ldap user filter" and "ldap group filter". Bug #526.
+ * NEW: Option "vol dbnest", when set to true, the CNID database for
+ a volume is stored in the volume root of a share in a directory
+ .AppleDB like in Netatalk 2. Defaults to false. From FR#84.
+ * FIX: Small fix in the DSI tickle handling. Bug #528.
+ * UPD: Enhance handling of connection attempts when hitting the
+ connection limit. Bug #529.
+ * FIX: Saving from Word to a folder that is a symlink to a folder on
+ another filesystem results in a crash of the afpd process and
+ the save to fail. This happens only if the option
+ "follow symlinks" is enabled. Bug #532.
+ * FIX: Disable Kerberos UAM if AFP service principal name can't be
+ evaluated. Fixes bug #531.
Changes in 3.0.5
================
<listitem>
<para>Speficy a set of file and directory attributes that shall
- be ignored by the server, <attribute>all</attribute> includes all
+ be ignored by the server, <option>all</option> includes all
the other options.</para>
<para>In OS X when the Finder sets a lock on a file/directory or you
set the BSD uchg flag in the Terminal, all three attributes are
</listitem>
</varlistentry>
+ <varlistentry>
+ <term>spotlight =
+ <replaceable>BOOLEAN</replaceable> (default:
+ <emphasis>no</emphasis>) <type>(G)/(V)</type></term>
+
+ <listitem>
+ <para>Whether to enable Spotlight searches. Note: once the global
+ option is enabled, any volume that is not enabled won't be
+ searchable at all.</para>
+ </listitem>
+ </varlistentry>
+
<varlistentry>
<term>veto message = <replaceable>BOOLEAN</replaceable> (default:
<emphasis>no</emphasis>) <type>(G)</type></term>
</listitem>
</varlistentry>
+ <varlistentry>
+ <term>vol dbnest = <replaceable>BOOLEAN</replaceable> (default:
+ <emphasis>no</emphasis>) <type>(G)</type></term>
+
+ <listitem>
+ <para>Setting this option to true brings back Netatalk 2
+ behaviour of storing the CNID database in a folder called
+ .AppleDB inside the volume root of each share.</para>
+ </listitem>
+ </varlistentry>
+
<varlistentry>
<term>volnamelen = <replaceable>number</replaceable>
<type>(G)</type></term>
mode. You can adjust this behaviour with the configuration option
<option>mac acls</option>:</para>
- <variablelist id="mac_acls">
+ <variablelist id="map_acls">
<varlistentry>
<term>map acls = <parameter>none|rights|mode</parameter>
<type>(G)</type></term>
Setting the option to true causes afpd to follow symlinks on the
server. symlinks may point outside of the AFP volume, currently
afpd doesn't do any checks for "wide symlinks".</para>
+ <note>
+ <para>This option will subtly break when the symlinks point
+ across filesystem boundaries.</para>
+ </note>
</listitem>
</varlistentry>
#include <atalk/fce_api.h>
#include <atalk/globals.h>
#include <atalk/netatalk_conf.h>
+#include <atalk/spotlight.h>
#include "switch.h"
#include "auth.h"
return;
}
- if ((err = pollvoltime(AFPobj)) == 0)
+ if ((err = pollvoltime(AFPobj)) == 0) {
LOG(log_debug, logtype_afpd, "afp_alarm: sending DSI tickle");
err = dsi_tickle(AFPobj->dsi);
+ }
if (err <= 0) {
if (geteuid() == 0) {
LOG(log_note, logtype_afpd, "afp_alarm: unauthenticated user, connection problem");
int flag = 1;
setsockopt(dsi->socket, SOL_TCP, TCP_NODELAY, &flag, sizeof(flag));
+ /* Initialize Spotlight */
+ if ((obj->options.flags & OPTION_SPOTLIGHT) && (obj->options.slmod_path))
+ sl_mod_load(obj->options.slmod_path);
+
ipc_child_state(obj, DSI_RUNNING);
/* get stuck here until the end */
#include <atalk/server_ipc.h>
#include <atalk/uuid.h>
#include <atalk/globals.h>
+#include <atalk/spotlight.h>
#include <atalk/unix.h>
#include "auth.h"
case 31:
uam_afpserver_action(AFP_SYNCDIR, UAM_AFPSERVER_POSTAUTH, afp_syncdir, NULL);
uam_afpserver_action(AFP_SYNCFORK, UAM_AFPSERVER_POSTAUTH, afp_syncfork, NULL);
- uam_afpserver_action(AFP_SPOTLIGHT_PRIVATE, UAM_AFPSERVER_POSTAUTH, afp_null_nolog, NULL);
+ uam_afpserver_action(AFP_SPOTLIGHT_PRIVATE, UAM_AFPSERVER_POSTAUTH, afp_spotlight_rpc, NULL);
uam_afpserver_action(AFP_ENUMERATE_EXT2, UAM_AFPSERVER_POSTAUTH, afp_enumerate_ext2, NULL);
case 30:
return AFPERR_NOTAUTH;
}
+ if (obj->cnx_cnt > obj->cnx_max) {
+ LOG(log_error, logtype_dsi, "login: too many connections, limit: %d", obj->cnx_max);
+ return AFPERR_MAXSESS;
+ }
+
LOG(log_note, logtype_afpd, "%s Login by %s",
afp_versions[afp_version_index].av_name, pwd->pw_name);
}
/* load all of the modules */
- int auth_load(const char *path, const char *list)
+ int auth_load(AFPObj *obj, const char *path, const char *list)
{
char name[MAXPATHLEN + 1], buf[MAXPATHLEN + 1], *p;
struct uam_mod *mod;
if ((stat(name, &st) == 0) && (mod = uam_load(name, p))) {
*/
if (stat(name, &st) == 0) {
- if ((mod = uam_load(name, p))) {
+ if ((mod = uam_load(obj, name, p))) {
uam_attach(&uam_modules, mod);
LOG(log_debug, logtype_afpd, "uam: %s loaded", p);
} else {
return ret;
}
- static int uam_setup(const char *path)
+ static int uam_setup(void *obj, const char *path)
{
if (uam_register(UAM_SERVER_LOGIN_EXT, path, "DHX2", pam_login,
pam_logincont, pam_logout, pam_login_ext) < 0)
gcry_mpi_release(g);
}
-
UAM_MODULE_EXPORT struct uam_export uams_dhx2 = {
UAM_MODULE_SERVER,
UAM_MODULE_VERSION,
#define OPTION_ACL2MODE (1 << 10)
#define OPTION_SHARE_RESERV (1 << 11) /* whether to use Solaris fcntl F_SHARE locks */
#define OPTION_DBUS_AFPSTATS (1 << 12) /* whether to run dbus thread for afpstats */
+#define OPTION_SPOTLIGHT (1 << 13) /* whether to initialize Spotlight support */
+#define OPTION_SPOTLIGHT_VOL (1 << 14) /* whether spotlight shall be enabled by default for volumes */
#define PASSWD_NONE 0
#define PASSWD_SET (1 << 0)
char *signatureopt;
unsigned char signature[16];
char *k5service, *k5realm, *k5keytab;
+ size_t k5principal_buflen;
+ char *k5principal;
char *unixcodepage, *maccodepage, *volcodepage;
charset_t maccharset, unixcharset;
mode_t umask;
char *mimicmodel;
char *adminauthuser;
char *ignored_attr;
+ char *slmod_path;
struct afp_volume_name volfile;
};
gid_t *groups;
int ngroups;
int afp_version;
+ int cnx_cnt, cnx_max;
/* Functions */
void (*logout)(void);
void (*exit)(int);
for(i = 0; i < vlen; i++)
if(tmpname[i] == '/') tmpname[i] = ':';
- bstring dbpath;
- EC_NULL( val = atalk_iniparser_getstring(obj->iniconfig, INISEC_GLOBAL, "vol dbpath", _PATH_STATEDIR "CNID/") );
- EC_NULL( dbpath = bformat("%s/%s/", val, tmpname) );
- EC_NULL( volume->v_dbpath = strdup(cfrombstr(dbpath)) );
- bdestroy(dbpath);
+
+ if (!atalk_iniparser_getboolean(obj->iniconfig, INISEC_GLOBAL, "vol dbnest", 0)) {
+ bstring dbpath;
+ EC_NULL( val = atalk_iniparser_getstring(obj->iniconfig, INISEC_GLOBAL, "vol dbpath", _PATH_STATEDIR "CNID/") );
+ EC_NULL( dbpath = bformat("%s/%s/", val, tmpname) );
+ EC_NULL( volume->v_dbpath = strdup(cfrombstr(dbpath)) );
+ bdestroy(dbpath);
+ } else {
+ EC_NULL( volume->v_dbpath = strdup(path) );
+ }
if ((val = getoption(obj->iniconfig, section, "cnid scheme", preset, NULL)))
EC_NULL( volume->v_cnidscheme = strdup(val) );
volume->v_flags |= AFPVOL_NOV2TOEACONV;
if (getoption_bool(obj->iniconfig, section, "follow symlinks", preset, 0))
volume->v_flags |= AFPVOL_FOLLOWSYM;
+ if (getoption_bool(obj->iniconfig, section, "spotlight", preset, obj->options.flags & OPTION_SPOTLIGHT_VOL)) {
+ volume->v_flags |= AFPVOL_SPOTLIGHT;
+ obj->options.flags |= OPTION_SPOTLIGHT;
+ }
if (getoption_bool(obj->iniconfig, section, "delete veto files", preset, 0))
volume->v_flags |= AFPVOL_DELVETO;
initvol_vfs(volume);
/* get/store uuid from file in afpd master*/
- if (!(pwd) && (volume->v_flags & AFPVOL_TM)) {
- char *uuid = get_vol_uuid(obj, volume->v_localname);
- if (!uuid) {
- LOG(log_error, logtype_afpd, "Volume '%s': couldn't get UUID",
- volume->v_localname);
- } else {
- volume->v_uuid = uuid;
- LOG(log_debug, logtype_afpd, "Volume '%s': UUID '%s'",
- volume->v_localname, volume->v_uuid);
- }
+ become_root();
+ char *uuid = get_vol_uuid(obj, volume->v_localname);
+ unbecome_root();
+ if (!uuid) {
+ LOG(log_error, logtype_afpd, "Volume '%s': couldn't get UUID",
+ volume->v_localname);
+ } else {
+ volume->v_uuid = uuid;
+ LOG(log_debug, logtype_afpd, "Volume '%s': UUID '%s'",
+ volume->v_localname, volume->v_uuid);
}
/* no errors shall happen beyond this point because the cleanup would mess the volume chain up */
options->configfile = AFPObj->cmdlineconfigfile ? strdup(AFPObj->cmdlineconfigfile) : strdup(_PATH_CONFDIR "afp.conf");
options->sigconffile = strdup(_PATH_STATEDIR "afp_signature.conf");
options->uuidconf = strdup(_PATH_STATEDIR "afp_voluuid.conf");
+#ifdef HAVE_TRACKER_SPARQL
+ options->slmod_path = strdup(_PATH_AFPDUAMPATH "slmod_sparql.so");
+#endif
options->flags = OPTION_UUID | AFPObj->cmdlineflags;
if ((config = atalk_iniparser_load(AFPObj->options.configfile)) == NULL)
options->flags |= OPTION_DBUS_AFPSTATS;
if (atalk_iniparser_getboolean(config, INISEC_GLOBAL, "afp read locks", 0))
options->flags |= OPTION_AFP_READ_LOCK;
+ if (atalk_iniparser_getboolean(config, INISEC_GLOBAL, "spotlight", 0))
+ options->flags |= OPTION_SPOTLIGHT_VOL;
if (atalk_iniparser_getboolean(config, INISEC_GLOBAL, "veto message", 0))
options->flags |= OPTION_VETOMSG;
if (!atalk_iniparser_getboolean(config, INISEC_GLOBAL, "save password", 1))
CONFIG_ARG_FREE(obj->options.k5service);
if (obj->options.k5realm)
CONFIG_ARG_FREE(obj->options.k5realm);
+ if (obj->options.k5principal)
+ CONFIG_ARG_FREE(obj->options.k5principal);
if (obj->options.listen)
CONFIG_ARG_FREE(obj->options.listen);
if (obj->options.interfaces)
CONFIG_ARG_FREE(obj->options.fqdn);
if (obj->options.ignored_attr)
CONFIG_ARG_FREE(obj->options.ignored_attr);
+ if (obj->options.slmod_path)
+ CONFIG_ARG_FREE(obj->options.slmod_path);
if (obj->options.unixcodepage)
CONFIG_ARG_FREE(obj->options.unixcodepage);
ignored attributes = \fIall | nowrite | nodelete | norename\fR \fB(G)/(V)\fR
.RS 4
Speficy a set of file and directory attributes that shall be ignored by the server,
-<attribute>all</attribute>
+\fBall\fR
includes all the other options\&.
.sp
In OS X when the Finder sets a lock on a file/directory or you set the BSD uchg flag in the Terminal, all three attributes are used\&. Thus in order to ignore the Finder lock/BSD uchg flag, add set
Use share reservations on Solaris\&. Solaris CIFS server uses this too, so this makes a lock coherent multi protocol server\&.
.RE
.PP
+spotlight = \fIBOOLEAN\fR (default: \fIno\fR) \fB(G)/(V)\fR
+.RS 4
+Whether to enable Spotlight searches\&. Note: once the global option is enabled, any volume that is not enabled won\*(Aqt be searchable at all\&.
+.RE
+.PP
veto message = \fIBOOLEAN\fR (default: \fIno\fR) \fB(G)\fR
.RS 4
Send optional AFP messages for vetoed files\&. Then whenever a client tries to access any file or directory with a vetoed name, it will be sent an AFP message indicating the name and the directory\&.
@localstatedir@/netatalk/CNID/\&.
.RE
.PP
+ vol dbnest = \fIBOOLEAN\fR (default: \fIno\fR) \fB(G)\fR
+ .RS 4
+ Setting this option to true brings back Netatalk 2 behaviour of storing the CNID database in a folder called \&.AppleDB inside the volume root of each share\&.
+ .RE
+ .PP
volnamelen = \fInumber\fR \fB(G)\fR
.RS 4
Max length of UTF8\-MAC volume name for Mac OS X\&. Note that Hangul is especially sensitive to this\&.
follow symlinks = \fIBOOLEAN\fR (default: \fIno\fR) \fB(V)\fR
.RS 4
The default setting is false thus symlinks are not followed on the server\&. This is the same behaviour as OS X\*(Aqs AFP server\&. Setting the option to true causes afpd to follow symlinks on the server\&. symlinks may point outside of the AFP volume, currently afpd doesn\*(Aqt do any checks for "wide symlinks"\&.
+ .if n \{\
+ .sp
+ .\}
+ .RS 4
+ .it 1 an-trap
+ .nr an-no-space-flag 1
+ .nr an-break-flag 1
+ .br
+ .ps +1
+ \fBNote\fR
+ .ps -1
+ .br
+ This option will subtly break when the symlinks point across filesystem boundaries\&.
+ .sp .5v
+ .RE
.RE
.PP
invisible dots = \fIBOOLEAN\fR (default: \fIno\fR) \fB(V)\fR