home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
The CDPD Public Domain Collection for CDTV 3
/
CDPDIII.bin
/
pd
/
commodities
/
superdark
/
main
/
main.c
< prev
next >
Wrap
C/C++ Source or Header
|
1993-03-21
|
16KB
|
616 lines
/************************************************************************/
/* */
/* File main.c */
/* */
/************************************************************************/
/* This is the main entry point of SuperDark. Open all the ressources, */
/* and call the other function. Also look for all the availables */
/* modules and launch them */
/* */
/************************************************************************/
#include <exec/types.h>
#include <exec/nodes.h>
#include <exec/ports.h>
#include <exec/memory.h>
#include <intuition/intuition.h>
#include <intuition/gadgetclass.h>
#include <libraries/gadtools.h>
#include <libraries/reqtools.h>
#include <clib/exec_protos.h>
#include <graphics/displayinfo.h>
#include <dos/dos.h>
#include <dos/dosextens.h>
#include <clib/dos_protos.h>
#include <workbench/startup.h>
#include "/includes/struct.h"
#include "/includes/tom_gadget.h"
#include "gid_main.h"
#ifndef WB_13
struct Library *CxBase;
#endif
struct Library *GadToolsBase;
struct Library *IconBase;
struct Library *IntuitionBase;
struct Library *GfxBase;
struct Library *CxBase;
struct ReqToolsBase *ReqToolsBase;
extern struct my_data my_info;
extern struct tom_gadget my_gadg[];
extern struct tom_gadget gadg_alea[];
#define STRLEN_DARK 5 /* Equivalent to strlen(".dark") */
struct contexe big_ctx;
/* Structure qui sauvegarde les parametres */
int selection=-1; /* Numero de l'effet selectionne */
int last_sel=-1; /* dernier numero selecitonne */
BPTR segment=0;
int flg_end; /* Drapeau indiquant la sortie du prog */
UBYTE flg_debug=FALSE;
char *p_name;
UBYTE flg_prog_dark;
UBYTE flg_port_created;
struct WBStartup my_msg;
struct Process *process;
extern struct appel_proc data_proc;
char p_dark[]="That's Dark!";
int nb_module=0;
char *p_nom[MAX_NOM];
struct Node ModulesNodes[MAX_NOM];
struct List *mode_liste;
#define RANDOM "Random"
char *p_alea=RANDOM;
struct Node alea_node={0,0,0,0,
RANDOM};
BPTR old_lock=-1;
struct MsgPort *rep=0;
char buffer[100];
extern char buffer_effet[];
LONG dir_save=0;
char p_ver[]="\0$VER: SuperDark 1.4 (20/03/93)";
struct List ModulesList = {
( struct Node * )&ModulesList.lh_Tail,
( struct Node * )0l,
( struct Node * )&ModulesList.lh_Head,0,0 };
/*********************************************************** aff_error() */
void aff_error(char *p_texte)
{
affiche_texte(p_texte,NULL,NULL);
}
/************************************************************ set_ext() */
/* remove evrything */
void stop()
{
big_ctx.flg_end=TRUE;
}
/************************************************************ set_ext() */
/* open window */
void show()
{
show_win(&big_ctx);
}
/************************************************************ set_ext() */
void set_ext(char *pc)
{
pc[strlen(pc)]='.';
}
/************************************************************ unset_ext() */
void unset_ext(char *pc)
{
pc[strlen(pc)-STRLEN_DARK]=0;
}
/************************************************************ fin_mod() */
/*****************************************************/
/* This function look for the availables modules in: */
/* - the directory saved in the .info file as a */
/* tool type */
/* - then look in the current directory */
/*****************************************************/
int find_mod(char *name_dir)
{
struct Process *process;
int flg_err;
int etape,i,len;
struct FileInfoBlock *fib;
BPTR lt;
char *p;
UBYTE flg_deuxieme_passe;
flg_err=FALSE;
etape=0;
lt=0;
fib=0;
flg_deuxieme_passe=FALSE;
process = (struct Process *)FindTask(0);
do{
printd("find mod,etape:%ld\n",etape);
switch(etape){
case 0:
/* Allocation memoire pour le FileInfo Block */
/* Je rapelle aue le fib doit etre aligne sur */
/* un mot long....merci les BPTR */
if(fib==0){
if((fib=(struct FileInfoBlock *)AllocMem(sizeof(struct FileInfoBlock),0))==0){
flg_err=TRUE;
}
}
break;
case 1:
/* On cherche dans le repertoire passe dans le */
/* .info, si celui -ci existe.. */
if(name_dir!=0){
if(*name_dir!=0){
len=strlen(name_dir);
if(name_dir[len-1]=='/'){
name_dir[len-1]=0;
}
lt=Lock(name_dir,ACCESS_READ);
if(lt!=0){
old_lock=CurrentDir(lt);
printd("new dir ok %lx old:%lx\n",lt,old_lock);
}else{
printd("Lock de %s failed!\n",name_dir);
}
}
}
break;
case 2:
/* Si on n'a pas reussi a locke le repertoire donne */
/* on cherche dans le repertoire courant */
if(lt==0){
flg_deuxieme_passe=TRUE;
lt=process->pr_CurrentDir;
if(lt==0){
flg_err=TRUE;
aff_error("Erreur avec current dir");
}
}
break;
case 3:
/* On examine le repertoire */
printd("Avant le examine:lt:%lx fib:%lx\n",lt,fib);
if(Examine(lt,fib)==0){
aff_error("Erreur examine....\n");
flg_err=TRUE;
}
break;
case 4:
/* On examine d'abord les fichiers */
while(ExNext(lt,fib)!=NULL){
if(fib->fib_DirEntryType<0){
if(strlen(fib->fib_FileName)>5){
p=fib->fib_FileName+strlen(fib->fib_FileName)-5;
/* This is the correction of the 'Usnet' */
/* bug....so superdark if case indepdt. */
for(i=1;i<5;i++){
p[i]=tolower(p[i]);
}
if(strcmp(p,".dark")==0){
if(nb_module<MAX_NOM-1){
p_nom[nb_module]=(char *)malloc(strlen(fib->fib_FileName)+1);
strcpy(p_nom[nb_module],fib->fib_FileName);
unset_ext(p_nom[nb_module]);
nb_module++;
}else{
SPrintF(buffer,"ERROR:Max number of modules exceded(%ld)\n",MAX_NOM);
aff_error(buffer);
}
}
}
}
}
break;
case 5:
/* Si on n'avait trouve aucun module, on re-essaye */
/* une deuxieme fois dans le repertoire courant */
if((nb_module==0)&&(flg_deuxieme_passe==FALSE)&&(lt!=0)){
printd("Deuxieme passage:lt:%x,old_lock:%x\n",lt,old_lock);
CurrentDir(lt);
printd("Je fais un CurrentDir....new:%lx\n",lt);
lt=0;
etape=3-1;
}
break;
}
etape++;
/* Tant qu'il y a des etapes a effectuer */
}while((etape<6)&&(flg_err==FALSE));
if(nb_module!=0){
tqsort(p_nom,nb_module);
p_nom[nb_module]=p_alea;
for(i=0;i<nb_module;i++){
ModulesNodes[i].ln_Name=p_nom[i];
ModulesNodes[i].ln_Type=0;
AddTail(&ModulesList,&ModulesNodes[i]);
if(strcmp(p_nom[i],buffer_effet)==0){
selection=i;
}
}
AddTail(&ModulesList,&alea_node);
my_info.tempo_end=10;
if(selection==-1){
my_info.flg_alea=TRUE;
selection=nb_module;
}
my_gadg[GID_MODULES].value=selection;
}else{
/*
flg_err=1;
*/
if(name_dir!=0){
SPrintF(buffer,"No dark modules was found in the dir:\n\n%s\n\nHave you put the good directory in the\nTool type DARK DIRECTORY ?\n",name_dir);
}else{
SPrintF(buffer,"No dark modules was found!\nHave you put the good directory in the\nTool type DARK DIRECTORY ?\n",name_dir);
}
if(old_lock!=-1){
printd("je remt old_lock:%x\n",old_lock);
CurrentDir(old_lock);
}
aff_error(buffer);
}
if(fib!=0)FreeMem(fib,sizeof(struct FileInfoBlock));
return(flg_err);
}
/************************************************************ init_port *****/
int init_port()
{
struct MsgPort *mp;
struct appel_proc *ap;
srand(VBeamPos());
my_info.sigstart=-1;
my_info.sigshow=-1;
my_info.sigstop=-1;
my_info.signext=-1;
rep=(struct MsgPort *)CreatePort("Reponse",NULL);
my_info.flg_alea=FALSE;
flg_port_created=FALSE;
if((ap=(struct appel_proc *)FindPort(p_dark))==0){
mp=&data_proc.mp;
mp->mp_Node.ln_Name=p_dark;
mp->mp_Node.ln_Pri=0;
mp->mp_Node.ln_Type=NT_MSGPORT;
mp->mp_Flags=PA_IGNORE;
AddPort(&data_proc.mp);
my_info.tempo=100;
data_proc.p_info=&my_info;
flg_port_created=TRUE;
return(FALSE);
}else{
printd("Dark deja demarre!\n");
/**********************************/
/* On force la fenetre a s'ouvrir */
/**********************************/
#ifdef WB_13
/* En 1.3, sans commodities, on envoi le signal a l'autre */
/* tache et on sort */
Signal(ap->p_info->task,1<<(ap->p_info->sigshow));
return(TRUE);
#else
/* en 2.0, l'autre blanker recevral e msg UNIQUE, et celui */
/* (le nouveau) sortira lors du CxBroker */
return(FALSE);
#endif
}
}
/************************************************************ remove_seg() ***/
void remove_seg()
{
if(segment!=0){
Signal(&process->pr_Task,SIG_MAIN_DARK_EXIT);
WaitPort(rep);
GetMsg(rep);
UnLoadSeg(segment);
segment=0;
}
}
/*************************************************************** free_mod() **/
void free_mod()
{
int i;
for(i=0;i<nb_module;i++){
free(p_nom[i]);
}
while(RemHead(&ModulesList));
nb_module=0;
remove_seg();
}
/*************************************************************** do_dark() **/
void do_dark()
{
int num_module;
struct Task *mt;
int i;
if(((last_sel!=selection)||(segment==0))&&(nb_module!=0)){
if(segment!=0){
Signal(&process->pr_Task,SIG_MAIN_DARK_EXIT);
printd("J'attend le message de l'exit!\n");
WaitPort(rep);
GetMsg(rep);
UnLoadSeg(segment);
}
num_module=selection%nb_module;
last_sel=selection;
data_proc.p_texte=0;
set_ext(p_nom[num_module]);
printd("Je charge le %ld qui est:[%s]\n",num_module,p_nom[num_module]);
segment=LoadSeg(p_nom[num_module]);
if(segment!=0){
/************************************************/
/* We create a new task, with a given taskpri */
/* Note: be carefull, the processe struct is not*/
/* at the same adresse than the task struct. */
/* Note2: The task is created with a high */
/* priority, but this priority is changed just */
/* after. */
/************************************************/
process=(struct Process *)((char *)CreateProc(p_nom[num_module],
0,
segment,
8192)-sizeof(struct Task));
mt=FindTask(0);
my_msg.sm_Message.mn_ReplyPort=&data_proc.mp;
my_msg.sm_Message.mn_ReplyPort=rep;
my_msg.sm_ToolWindow=0;
my_msg.sm_ArgList=0;
my_msg.sm_NumArgs=0;
process->pr_Task.tc_UserData=mt;
my_info.task_dark=&process->pr_Task;
PutMsg(&process->pr_MsgPort,(struct Msg *)&my_msg);
/***********************************************************/
/* On positionne le code retour, et on attend qu'il change */
/* d'etat, indiquant que l'init est OK. On ne peut pas */
/* de 'meilleur' type de communication, car on n'est pas */
/* sur que c'est un module pour dark, et on risquerqais */
/* alors de bloquer en attente de reponse */
/***********************************************************/
i=500;
data_proc.code_ret=-1;
flg_prog_dark=TRUE;
/* while((data_proc.code_ret==-1)&&(i-->0)){*/
while(data_proc.code_ret==-1){
Delay(1);
}
if(data_proc.code_ret==-1){
aff_error("ERROR:This is not a Dark Module!\n");
flg_prog_dark=FALSE;
}else{
SetTaskPri( &process->pr_Task,
my_gadg[GID_TASK_PRI].value);
printd("Loading conf\n");
LoadConfig(p_nom[num_module],data_proc.p_gadg);
}
#ifdef WB_13
/* Si c'est un module qui a besoin du WB2.0 */
/* il ne faut pas l'executer... */
if((data_proc.code_ret==DARK_WB_20)){
aff_error("This one need 2.0 to run!\n");
flg_prog_dark=FALSE;
}
#endif
}else{
aff_error("segment not found\n");
selection=-1;
}
unset_ext(p_nom[num_module]);
}
}
/*********************************************** Liberation des ressources **/
void free_all()
{
if(mode_liste!=0)free_modes(mode_liste);
remove_seg();
if(flg_port_created)RemPort(&data_proc.mp);
if(rep)RemPort(rep);
free_input_ev();
CleanStuff_gadg(&big_ctx);
if(old_lock!=-1){
CurrentDir(old_lock);
}
if(IconBase)CloseLibrary(IconBase);
#ifndef WB_13
if(CxBase)CloseLibrary(CxBase);
if(GadToolsBase)CloseLibrary(GadToolsBase);
#endif
if(IntuitionBase)CloseLibrary(IntuitionBase);
if(GfxBase)CloseLibrary(GfxBase);
if(ReqToolsBase)CloseLibrary ((struct Library *)ReqToolsBase);
}
/************************************************************ main *****/
/************************************************/
/* main function. Open the libs, and if all is */
/* ok, call the other functions */
/************************************************/
main(argc,argv)
int argc;
char *argv[];
{
int etape,flg_err,i;
struct WBStartup *WBenchMsg;
struct WBArg *wbarg;
LONG olddir;
extern struct List *get_modes();
i=1;
while(i<argc){
if(strcmp(argv[i],"-d")==0){
flg_debug=TRUE;
}
i++;
}
p_name=argv[0];
olddir=-1;
etape=0;
flg_err=FALSE;
while((flg_err==FALSE)&&(etape<7)){
printd("Etape:%ld\n",etape);
switch(etape){
case 0:
/* First, we open all the needed library */
IntuitionBase=(struct Library *)OpenLibrary("intuition.library",0);
GfxBase=(struct Library *)OpenLibrary("graphics.library",0);
IconBase=(struct Library *)OpenLibrary("icon.library",0);
#ifndef WB_13
/* CxBase=OpenLibrary("commodities.library",37L);*/
GadToolsBase=(struct Library *)OpenLibrary("gadtools.library",0);
if(GadToolsBase==0){
flg_err=TRUE;
aff_error("This doesn't seem to be a\nWB 2.0 or higher\n\nUse SuperDark_1.3\n\n");
}
CxBase=OpenLibrary("commodities.library",37L);
#endif
ReqToolsBase = (struct ReqToolsBase *)OpenLibrary (REQTOOLSNAME, REQTOOLSVERSION);
break;
/* initialisation du port de communication */
case 1:
flg_err=init_port();
break;
/* chargement des parametres de config */
case 2:
/* Du WB? */
if(argc==0){
WBenchMsg=(struct WBStartup *)argv;
for(i=0,wbarg=WBenchMsg->sm_ArgList;
i<WBenchMsg->sm_NumArgs;
i++,wbarg++){
if((wbarg->wa_Lock)&&(*wbarg->wa_Name)){
p_name=wbarg->wa_Name;
dir_save=wbarg->wa_Lock;
olddir=CurrentDir(dir_save);
printd("Je fais un CurrentDir..old:%lx new:%lx\n",olddir,dir_save);
}
}
}
LoadConfig(p_name,&my_gadg[GID_TEMPO]);
my_info.tempo=my_gadg[GID_TEMPO].value;
printd("Tempo:%ld\n",my_info.tempo);
/* Rem: les parametres du module aleatoire sont sauvegarde*/
/* avec ceux du fichier principal, car le mode aleatoire */
/* n'ayant pas d'icone... */
LoadConfig(p_name,gadg_alea);
break;
/* recherche des modules existants */
case 4:
flg_err=find_mod(my_gadg[GID_DIR].p_data);
break;
/* initialisation de l'input ev */
case 3:
#ifdef WB_13
flg_err=init_input_ev();
#endif
#ifndef WB_13
flg_err=init_input_ev(argc,argv);
#endif
break;
case 5:
/* chargement de la suite de la config du module aleatoire*/
load_alea_cfg();
/* We open the main window */
big_ctx.t_g=my_gadg;
big_ctx.GList=0;
big_ctx.p_name=p_name;
if(nb_module!=0)my_gadg[GID_MODULES].d2=nb_module-1;
break;
case 6:
/* Liste des modes dispo */
if((mode_liste=get_modes())==0){
flg_err=TRUE;
}
data_proc.ml=mode_liste;
break;
}
etape++;
}
if(flg_err==FALSE){
/* Si il n'y a aucun module, on ouvre la fentre, pour que */
/* l'utilisateur voi qq chose! */
if(nb_module==0){
InitStuff_gadg(&big_ctx,TRUE);
}else{
if(my_gadg[GID_QUIET].value==FALSE){
affiche_texte("SuperDark Installed...\nPress HotKey for options",NULL,TRUE);
}
}
main_loop(&big_ctx);
my_gadg[GID_MODULES].value=selection;
if(big_ctx.flg_save==TRUE){
SaveConfig(p_name,&my_gadg[GID_DEBUT]);
save_alea_cfg();
}
}
if(olddir!=-1)CurrentDir(olddir);
free_all();
}