2 * OpenAL cross platform audio library
3 * Copyright (C) 1999-2007 by authors.
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Library General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Library General Public License for more details.
14 * You should have received a copy of the GNU Library General Public
15 * License along with this library; if not, write to the
16 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17 * Boston, MA 02111-1307, USA.
18 * Or go to http://www.gnu.org/copyleft/lgpl.html
23 #define _WIN32_IE 0x501
25 #define _WIN32_IE 0x400
42 typedef struct ConfigEntry
{
47 typedef struct ConfigBlock
{
53 static ConfigBlock
*cfgBlocks
;
54 static size_t cfgCount
;
56 static char buffer
[1024];
58 static void LoadConfigFromFile(FILE *f
)
60 ConfigBlock
*curBlock
= cfgBlocks
;
63 while(fgets(buffer
, sizeof(buffer
), f
))
67 while(isspace(buffer
[i
]))
69 if(!buffer
[i
] || buffer
[i
] == '#')
72 memmove(buffer
, buffer
+i
, strlen(buffer
+i
)+1);
76 ConfigBlock
*nextBlock
;
79 while(buffer
[i
] && buffer
[i
] != ']')
84 AL_PRINT("config parse error: bad line \"%s\"\n", buffer
);
91 if(buffer
[i
] && !isspace(buffer
[i
]))
94 AL_PRINT("config warning: extra data after block: \"%s\"\n", buffer
+i
);
100 for(i
= 0;i
< cfgCount
;i
++)
102 if(strcasecmp(cfgBlocks
[i
].name
, buffer
+1) == 0)
104 nextBlock
= cfgBlocks
+i
;
105 // AL_PRINT("found block '%s'\n", nextBlock->name);
112 nextBlock
= realloc(cfgBlocks
, (cfgCount
+1)*sizeof(ConfigBlock
));
115 AL_PRINT("config parse error: error reallocating config blocks\n");
118 cfgBlocks
= nextBlock
;
119 nextBlock
= cfgBlocks
+cfgCount
;
122 nextBlock
->name
= strdup(buffer
+1);
123 nextBlock
->entries
= NULL
;
124 nextBlock
->entryCount
= 0;
126 // AL_PRINT("found new block '%s'\n", nextBlock->name);
128 curBlock
= nextBlock
;
132 /* Look for the option name */
134 while(buffer
[i
] && buffer
[i
] != '#' && buffer
[i
] != '=' &&
138 if(!buffer
[i
] || buffer
[i
] == '#' || i
== 0)
140 AL_PRINT("config parse error: malformed option line: \"%s\"\n", buffer
);
144 /* Seperate the option */
149 while(isspace(buffer
[i
]))
153 AL_PRINT("config parse error: option without a value: \"%s\"\n", buffer
);
157 /* Find the start of the value */
159 while(isspace(buffer
[i
]))
162 /* Check if we already have this option set */
163 ent
= curBlock
->entries
;
164 while((size_t)(ent
-curBlock
->entries
) < curBlock
->entryCount
)
166 if(strcasecmp(ent
->key
, buffer
) == 0)
171 if((size_t)(ent
-curBlock
->entries
) >= curBlock
->entryCount
)
173 /* Allocate a new option entry */
174 ent
= realloc(curBlock
->entries
, (curBlock
->entryCount
+1)*sizeof(ConfigEntry
));
177 AL_PRINT("config parse error: error reallocating config entries\n");
180 curBlock
->entries
= ent
;
181 ent
= curBlock
->entries
+ curBlock
->entryCount
;
182 curBlock
->entryCount
++;
184 ent
->key
= strdup(buffer
);
188 /* Look for the end of the line (Null term, new-line, or #-symbol) and
189 eat up the trailing whitespace */
190 memmove(buffer
, buffer
+i
, strlen(buffer
+i
)+1);
193 while(buffer
[i
] && buffer
[i
] != '#' && buffer
[i
] != '\n')
197 } while(isspace(buffer
[i
]));
201 ent
->value
= strdup(buffer
);
203 // AL_PRINT("found '%s' = '%s'\n", ent->key, ent->value);
207 void ReadALConfig(void)
211 cfgBlocks
= calloc(1, sizeof(ConfigBlock
));
212 cfgBlocks
->name
= strdup("general");
216 if(SHGetSpecialFolderPathA(NULL
, buffer
, CSIDL_APPDATA
, FALSE
) != FALSE
)
218 size_t p
= strlen(buffer
);
219 snprintf(buffer
+p
, sizeof(buffer
)-p
, "\\alsoft.ini");
220 f
= fopen(buffer
, "rt");
223 LoadConfigFromFile(f
);
228 f
= fopen("/etc/openal/alsoft.conf", "r");
231 LoadConfigFromFile(f
);
234 if(getenv("HOME") && *(getenv("HOME")))
236 snprintf(buffer
, sizeof(buffer
), "%s/.alsoftrc", getenv("HOME"));
237 f
= fopen(buffer
, "r");
240 LoadConfigFromFile(f
);
245 if(getenv("ALSOFT_CONF"))
247 f
= fopen(getenv("ALSOFT_CONF"), "r");
250 LoadConfigFromFile(f
);
256 void FreeALConfig(void)
260 for(i
= 0;i
< cfgCount
;i
++)
263 for(j
= 0;j
< cfgBlocks
[i
].entryCount
;j
++)
265 free(cfgBlocks
[i
].entries
[j
].key
);
266 free(cfgBlocks
[i
].entries
[j
].value
);
268 free(cfgBlocks
[i
].entries
);
269 free(cfgBlocks
[i
].name
);
276 const char *GetConfigValue(const char *blockName
, const char *keyName
, const char *def
)
284 blockName
= "general";
286 for(i
= 0;i
< cfgCount
;i
++)
288 if(strcasecmp(cfgBlocks
[i
].name
, blockName
) != 0)
291 for(j
= 0;j
< cfgBlocks
[i
].entryCount
;j
++)
293 if(strcasecmp(cfgBlocks
[i
].entries
[j
].key
, keyName
) == 0)
295 if(cfgBlocks
[i
].entries
[j
].value
[0])
296 return cfgBlocks
[i
].entries
[j
].value
;
305 int ConfigValueExists(const char *blockName
, const char *keyName
)
307 const char *val
= GetConfigValue(blockName
, keyName
, "");
311 int GetConfigValueInt(const char *blockName
, const char *keyName
, int def
)
313 const char *val
= GetConfigValue(blockName
, keyName
, "");
315 if(!val
[0]) return def
;
316 return strtol(val
, NULL
, 0);
319 float GetConfigValueFloat(const char *blockName
, const char *keyName
, float def
)
321 const char *val
= GetConfigValue(blockName
, keyName
, "");
323 if(!val
[0]) return def
;
325 return strtof(val
, NULL
);
327 return (float)strtod(val
, NULL
);
331 int GetConfigValueBool(const char *blockName
, const char *keyName
, int def
)
333 const char *val
= GetConfigValue(blockName
, keyName
, "");
335 if(!val
[0]) return !!def
;
336 return (strcasecmp(val
, "true") == 0 || strcasecmp(val
, "yes") == 0 ||
337 strcasecmp(val
, "on") == 0 || atoi(val
) != 0);