As some of you may recall, I was brainstorming on IMC yesterday about being able to transfer a descriptor from one MUD to another.
The basic premise of this is to be able to connect to a MUD, and be able to move that connection to another mud on the same machine without booting the character. (Think about making an exit in a room to another plane of existence, going through that exit and arriving in an entirely new world, eg. another MUD)
For some background information, the codebases would be generally the same, perhaps scaled down a bit for the lesser one, with different areas and possibly different classes/skill sets.
Also of note, a character can be logged in to only one MUD or the other, never both on the same character. Assume both MUDs use the same pfile to read/write to.
My idea is to use IPC shared memory space to do this, but I have some problems getting the actual code worked out because my knowledge of IPC is limited and there is not a great deal of applicable help out there.
The basic design is this:
Character connects and logs into MUD A as normal.
Character does something to trigger the transfer to MUD B (Doesn't really matter what the trigger is, that's simple)
MUD A copies the character's descriptor data to a shared memory space using IPC
MUD A notifies MUD B that there is a transfer to be made via IPC messaging queues and tells it the shared memory key.
MUD B responds that it received the message and accesses the shared memory space using the given key and creates a descriptor with the accessed information.
MUD B places a pointer to the new descriptor it made in shared memory with a different key and notifies MUD A with the new key.
MUD A accesses the shared memory with the new key and moves the character's descriptor pointer to the new one in shared memory, I'm assuming this will effectively move the character to the new section of memory in MUD B.
Does anyone see any issues with this? Here is an example I was testing last night to store data in shared memory using IPC:
CMDF do_socktest( CHAR_DATA *ch, char *argument )
{
int key;
int shmid;
char *data;
static short SHM_SIZE = 1024;
key = 666;
/* connect to (and possibly create) the segment: */
if( (shmid = shmget(key, SHM_SIZE, 0644 | IPC_CREAT)) == -1 )
{
bug("shmget"
;
return;
}
/* attach to the segment to get a pointer to it: */
data = (char *) shmat(shmid, (void *)0, 0);
if( data == (char *)(-1) )
{
bug("shmat"
;
return;
}
/* read or modify the segment, based on the command line: */
if( !NULLSTR(argument) )
{
ch_printf(ch, "writing to segment: \"%s\"\n", argument );
strncpy(data, argument, SHM_SIZE);
}
else
ch_printf(ch, "segment contains: \"%s\"\n", data);
/* detach from the segment: */
if (shmdt(data) == -1)
{
bug("shmdt"
;
return;
}
return;
}
My problem is I don't quite understand how to store a whole data structure in this space just yet. I also am not certain that by storing the descriptor data from MUD A in shared memory, accessing it with MUD B and recreating the data there and replacing the data in shared memory with a pointer to the data on MUD B will allow me to reassign the descriptor to this new address and effectively move the character in memory to a different MUD.
Perhaps something like this to store it:
struct descriptor_data *d;
d = ch->desc;
shmget(key, sizeof(d), 0644 | IPC_CREAT)
And some function to copy it on the other mud, followed by the above a second time to store the pointer to it, followed by something like this to move the pointer:
struct descriptor_data *data;
data = shmat(shmid, (void *)0, 0);
ch->desc = data;
Any insight you guys can give me this would be very helpful.
Exo