/*
* Server functions which perform operations on room objects.
*
- * Copyright (c) 1987-2012 by the citadel.org team
+ * Copyright (c) 1987-2016 by the citadel.org team
*
* This program is open source software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License, version 3.
#include <libcitadel.h>
#include "citserver.h"
-
#include "ctdl_module.h"
#include "config.h"
#include "control.h"
int CtdlDoIHavePermissionToReadMessagesInThisRoom(void) {
if ( (!(CC->logged_in))
&& (!(CC->internal_pgm))
- && (!config.c_guest_logins)
+ && (!CtdlGetConfigInt("c_guest_logins"))
) {
return(om_not_logged_in);
}
}
- if ((CC->user.axlevel < AxProbU)
- && ((CC->room.QRflags & QR_MAILBOX) == 0)) {
+ if ((CC->user.axlevel < AxProbU) && ((CC->room.QRflags & QR_MAILBOX) == 0))
+ {
snprintf(errmsgbuf, n, "Need to be validated to enter (except in %s> to sysop)", MAILROOM);
return (ERROR + HIGHER_ACCESS_REQUIRED);
}
}
/*
- * Retrieve access control information for any user/room pair
+ * Retrieve access control information for any user/room pair.
+ * Yes, it has a couple of gotos. If you don't like that, go die in a car fire.
*/
void CtdlRoomAccess(struct ctdlroom *roombuf, struct ctdluser *userbuf,
int *result, int *view)
is_me = 1;
}
- if ((is_me) && (config.c_guest_logins) && (!CC->logged_in)) {
+ if ((is_me) && (CtdlGetConfigInt("c_guest_logins")) && (!CC->logged_in)) {
is_guest = 1;
}
}
/* Force the properties of the Aide room */
- if (!strcasecmp(roombuf->QRname, config.c_aideroom)) {
+ if (!strcasecmp(roombuf->QRname, CtdlGetConfigStr("c_aideroom"))) {
if (userbuf->axlevel >= AxAideU) {
retval = UA_KNOWN | UA_GOTOALLOWED | UA_POSTALLOWED | UA_DELETEALLOWED | UA_REPLYALLOWED;
} else {
}
/* Listing order of 0 is illegal except for base rooms */
if (qrbuf->QRorder == 0)
- if (!(qrbuf->QRflags & QR_MAILBOX) &&
- strncasecmp(qrbuf->QRname, config.c_baseroom, ROOMNAMELEN)
- &&
- strncasecmp(qrbuf->QRname, config.c_aideroom, ROOMNAMELEN))
+ if ( !(qrbuf->QRflags & QR_MAILBOX)
+ && strncasecmp(qrbuf->QRname, CtdlGetConfigStr("c_baseroom"), ROOMNAMELEN)
+ && strncasecmp(qrbuf->QRname, CtdlGetConfigStr("c_aideroom"), ROOMNAMELEN)
+ ) {
qrbuf->QRorder = 64;
+ }
}
}
}
+
/*
* CtdlGetRoomLock() - same as getroom() but locks the record (if supported)
*/
-int CtdlGetRoomLock(struct ctdlroom *qrbuf, char *room_name)
+int CtdlGetRoomLock(struct ctdlroom *qrbuf, const char *room_name)
{
register int retval;
retval = CtdlGetRoom(qrbuf, room_name);
*/
void CtdlPutRoomLock(struct ctdlroom *qrbuf)
{
-
CtdlPutRoom(qrbuf);
end_critical_section(S_ROOMS);
-
}
*/
void lgetfloor(struct floor *flbuf, int floor_num)
{
-
begin_critical_section(S_FLOORTAB);
CtdlGetFloor(flbuf, floor_num);
}
*/
void CtdlPutFloorLock(struct floor *flbuf, int floor_num)
{
-
CtdlPutFloor(flbuf, floor_num);
end_critical_section(S_FLOORTAB);
/*
* Traverse the room file...
*/
-void CtdlForEachNetCfgRoom(ForEachRoomNetCfgCallBack CB,
- void *in_data,
- RoomNetCfg filter)
+void CtdlForEachNetCfgRoom(ForEachRoomNetCfgCallBack CB, void *in_data, RoomNetCfg filter)
{
struct ctdlroom qrbuf;
struct cdbdata *cdbqr;
{
OneRoomNetCfg* RNCfg;
RNCfg = CtdlGetNetCfgForRoom(qrbuf.QRnumber);
- if ((RNCfg != NULL) &&
- ((filter == maxRoomNetCfg) ||
- (RNCfg->NetConfigs[filter] != NULL)))
+ if ((RNCfg != NULL) && ((filter == maxRoomNetCfg) || (RNCfg->NetConfigs[filter] != NULL)))
{
CB(&qrbuf, in_data, RNCfg);
}
+ // FIXME free RNCfg
}
}
}
/* Know the room ... but not if it's the page log room, or if the
* caller specified that we're only entering this room transiently.
*/
- if ((strcasecmp(CCC->room.QRname, config.c_logpages))
- && (transiently == 0) ) {
+ if ((strcasecmp(CCC->room.QRname, CtdlGetConfigStr("c_logpages"))) && (transiently == 0))
+ {
vbuf.v_flags = vbuf.v_flags & ~V_FORGET & ~V_LOCKOUT;
vbuf.v_flags = vbuf.v_flags | V_ACCESS;
}
if (retnew != NULL) *retnew = new_messages;
if (retoldest != NULL) *retoldest = oldest_message;
if (retnewest != NULL) *retnewest = newest_message;
- MSG_syslog(LOG_INFO, "<%s> %d new of %d total messages, oldest=%ld, newest=%ld\n",
+ MSG_syslog(LOG_INFO, "<%s> %d new of %d total messages, oldest=%ld, newest=%ld",
CCC->room.QRname, new_messages, total_messages, oldest_message, newest_message
);
*/
void convert_room_name_macros(char *towhere, size_t maxlen) {
if (!strcasecmp(towhere, "_BASEROOM_")) {
- safestrncpy(towhere, config.c_baseroom, maxlen);
+ safestrncpy(towhere, CtdlGetConfigStr("c_baseroom"), maxlen);
}
else if (!strcasecmp(towhere, "_MAIL_")) {
safestrncpy(towhere, MAILROOM, maxlen);
safestrncpy(towhere, USERDRAFTROOM, maxlen);
}
else if (!strcasecmp(towhere, "_BITBUCKET_")) {
- safestrncpy(towhere, config.c_twitroom, maxlen);
+ safestrncpy(towhere, CtdlGetConfigStr("c_twitroom"), maxlen);
}
else if (!strcasecmp(towhere, "_CALENDAR_")) {
safestrncpy(towhere, USERCALENDARROOM, maxlen);
long owner = 0L;
char actual_old_name[ROOMNAMELEN];
- syslog(LOG_DEBUG, "CtdlRenameRoom(%s, %s, %d)\n",
- old_name, new_name, new_floor);
+ syslog(LOG_DEBUG, "CtdlRenameRoom(%s, %s, %d)", old_name, new_name, new_floor);
if (new_floor >= 0) {
fl = CtdlGetCachedFloor(new_floor);
}
/* Reject change of floor for baseroom/aideroom */
- if (!strncasecmp(old_name, config.c_baseroom, ROOMNAMELEN) ||
- !strncasecmp(old_name, config.c_aideroom, ROOMNAMELEN)) {
+ if (!strncasecmp(old_name, CtdlGetConfigStr("c_baseroom"), ROOMNAMELEN) ||
+ !strncasecmp(old_name, CtdlGetConfigStr("c_aideroom"), ROOMNAMELEN))
+ {
new_floor = 0;
}
begin_critical_section(S_CONFIG);
/* If baseroom/aideroom name changes, update config */
- if (!strncasecmp(old_name, config.c_baseroom, ROOMNAMELEN)) {
- safestrncpy(config.c_baseroom, new_name, ROOMNAMELEN);
- put_config();
+ if (!strncasecmp(old_name, CtdlGetConfigStr("c_baseroom"), ROOMNAMELEN)) {
+ CtdlSetConfigStr("c_baseroom", new_name);
}
- if (!strncasecmp(old_name, config.c_aideroom, ROOMNAMELEN)) {
- safestrncpy(config.c_aideroom, new_name, ROOMNAMELEN);
- put_config();
+ if (!strncasecmp(old_name, CtdlGetConfigStr("c_aideroom"), ROOMNAMELEN)) {
+ CtdlSetConfigStr("c_aideroom", new_name);
}
end_critical_section(S_CONFIG);
lgetfloor(&flbuf, old_floor);
--flbuf.f_ref_count;
lputfloor(&flbuf, old_floor);
- syslog(LOG_DEBUG, "Reference count for floor %d is now %d\n", old_floor, flbuf.f_ref_count);
+ syslog(LOG_DEBUG, "Reference count for floor %d is now %d", old_floor, flbuf.f_ref_count);
lgetfloor(&flbuf, new_floor);
++flbuf.f_ref_count;
lputfloor(&flbuf, new_floor);
- syslog(LOG_DEBUG, "Reference count for floor %d is now %d\n", new_floor, flbuf.f_ref_count);
+ syslog(LOG_DEBUG, "Reference count for floor %d is now %d", new_floor, flbuf.f_ref_count);
}
/* ...and everybody say "YATTA!" */
}
-
/*
- * Asynchronously schedule a room for deletion. The room will appear
- * deleted to the user(s), but it won't actually get purged from the
- * database until THE DREADED AUTO-PURGER makes its next run.
+ * Asynchronously schedule a room for deletion. By placing the room into an invalid private namespace,
+ * the room will appear deleted to the user(s), but the session doesn't need to block while waiting for
+ * database operations to complete. Instead, the room gets purged when THE DREADED AUTO-PURGER makes
+ * its next run. Aren't we so clever?!!
*/
void CtdlScheduleRoomForDeletion(struct ctdlroom *qrbuf)
{
char old_name[ROOMNAMELEN];
static int seq = 0;
- syslog(LOG_NOTICE, "Scheduling room <%s> for deletion\n",
- qrbuf->QRname);
+ syslog(LOG_NOTICE, "Scheduling room <%s> for deletion", qrbuf->QRname);
safestrncpy(old_name, qrbuf->QRname, sizeof old_name);
-
CtdlGetRoom(qrbuf, qrbuf->QRname);
/* Turn the room into a private mailbox owned by a user who doesn't
);
qrbuf->QRflags |= QR_MAILBOX;
time(&qrbuf->QRgen); /* Use a timestamp as the new generation number */
-
CtdlPutRoom(qrbuf);
-
b_deleteroom(old_name);
}
void CtdlDeleteRoom(struct ctdlroom *qrbuf)
{
struct floor flbuf;
- char filename[100];
- /* TODO: filename magic? does this realy work? */
+ char filename[PATH_MAX];
+ char configdbkeyname[25];
- syslog(LOG_NOTICE, "Deleting room <%s>\n", qrbuf->QRname);
+ syslog(LOG_NOTICE, "Deleting room <%s>", qrbuf->QRname);
/* Delete the info file */
assoc_file_name(filename, sizeof filename, qrbuf, ctdl_info_dir);
assoc_file_name(filename, sizeof filename, qrbuf, ctdl_image_dir);
unlink(filename);
- /* Delete the room's network config file */
- assoc_file_name(filename, sizeof filename, qrbuf, ctdl_netcfg_dir);
- unlink(filename);
+ /* Delete the room's network configdb entry */
+ netcfg_keyname(configdbkeyname, qrbuf->QRnumber);
+ CtdlDelConfig(configdbkeyname);
/* Delete the messages in the room
* (Careful: this opens an S_ROOMS critical section!)
}
-
/*
* Check access control for deleting a room
*/
struct floor flbuf;
visit vbuf;
- syslog(LOG_DEBUG, "CtdlCreateRoom(name=%s, type=%d, view=%d)\n",
- new_room_name, new_room_type, new_room_view);
+ syslog(LOG_DEBUG, "CtdlCreateRoom(name=%s, type=%d, view=%d)", new_room_name, new_room_type, new_room_view);
if (CtdlGetRoom(&qrbuf, new_room_name) == 0) {
- syslog(LOG_DEBUG, "%s already exists.\n", new_room_name);
+ syslog(LOG_DEBUG, "Cannot create room <%s> - already exists", new_room_name);
return(0);
}