Centralize catgets() calls through MsgCat

CDE has relied upon catgets() implementations following a relaxed
interpretation of the XPG internationalization standard that ignored
-1, the standard error value returned by catopen, as the catalog
argument. However, this same behavior causes segmentation faults with
the musl C library.

This patch:

- Centralizes (with the exception of ToolTalk) all calls to catopen(),
  catgets(), and catclose() through MsgCat within the DtSvc library.
- Prevents calls to catgets() and catclose() that rely upon
  undefined behavior.
- Eliminates a number of bespoke catgets() wrappers, including multiple
  redundant caching implementations designed to work around a design
  peculiarity in HP/UX.
- Eases building CDE without XPG internationalization support by providing
  the appropriate macros.
This commit is contained in:
Lev Kujawski
2021-01-30 20:05:13 -07:00
committed by Jon Trulson
parent 3379999106
commit a6ea2a2d52
241 changed files with 3154 additions and 3498 deletions

View File

@@ -42,7 +42,7 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <nl_types.h>
#include <Dt/MsgCatP.h>
#include "DtSvcLock.h"
/*****************************************************************************
@@ -79,7 +79,7 @@ Dt11GetMessage(
_DtSvcProcessLock();
if ( NULL == nlmsg_filename || 0 != strcmp(nlmsg_filename, filename) )
{
nlmsg_fd = catopen(filename, NL_CAT_LOCALE);
nlmsg_fd = CATOPEN(filename, NL_CAT_LOCALE);
if (nlmsg_filename)
{
free(nlmsg_filename);
@@ -87,7 +87,7 @@ Dt11GetMessage(
}
nlmsg_filename = strdup(filename);
}
msg=catgets(nlmsg_fd,set,n,s);
msg=CATGETS(nlmsg_fd,set,n,s);
_DtSvcProcessUnlock();
return (msg);
}

View File

@@ -45,7 +45,7 @@
************************************<+>*************************************/
#include <stdio.h>
#include <nl_types.h>
#include <Dt/MsgCatP.h>
#include "DtSvcLock.h"
#if !defined(NL_CAT_LOCALE)
@@ -80,8 +80,6 @@ _DtGetMessage(
{
char *msg;
char *lang;
nl_catd catopen();
char *catgets();
static int first = 1;
static nl_catd nlmsg_fd;
@@ -89,9 +87,9 @@ _DtGetMessage(
if ( first )
{
first = 0;
nlmsg_fd = catopen(filename, NL_CAT_LOCALE);
nlmsg_fd = CATOPEN(filename, NL_CAT_LOCALE);
}
msg=catgets(nlmsg_fd,set,n,s);
msg=CATGETS(nlmsg_fd,set,n,s);
_DtSvcProcessUnlock();
return (msg);
}

View File

@@ -37,11 +37,18 @@
#include <stdio.h>
#include <string.h>
#include <nl_types.h>
#include <X11/Intrinsic.h>
#include <Dt/MsgCatP.h>
#include <DtSvcLock.h>
#if defined(NO_XLIB)
#define _DtSvcProcessLock()
#define _DtSvcProcessUnlock()
#else
#include <X11/Intrinsic.h>
#include <DtSvcLock.h>
#endif /* NO_XLIB */
#include <Dt/MsgCatP.h>
#if defined(hpV4) && !defined(NO_XLIB)
typedef struct _dt_msg_cache
{
char ***cached_msgs;
@@ -56,8 +63,8 @@ static _DtMsgCache *catalog_message_caches = NULL;
static _DtMsgCache *get_msg_cache(nl_catd catd)
{
#define INITIAL_NMSGS_PER_SET 300
#define INITIAL_NSETS 50
const int initial_nmsgs_per_set = 300;
const int initial_nsets = 50;
_DtMsgCache *c;
@@ -66,28 +73,23 @@ static _DtMsgCache *get_msg_cache(nl_catd catd)
c = (_DtMsgCache*) XtMalloc(sizeof(_DtMsgCache));
c->cached_msgs = NULL;
c->nmsgs_per_set = INITIAL_NMSGS_PER_SET;
c->nsets = INITIAL_NSETS;
c->nmsgs_per_set = initial_nmsgs_per_set;
c->nsets = initial_nsets;
c->catd = catd;
c->next = catalog_message_caches;
catalog_message_caches = c;
return c;
}
/*
* Wrapper around catgets -- this makes sure the message string is saved
* in a safe location; so repeated calls to catgets() do not overwrite
* the catgets() internal buffer. This has been a problem on HP systems.
*/
char *_DtCatgetsCached(nl_catd catd, int set, int num, char *dflt)
char *_DtCatgetsCached(nl_catd catd, int set, int num, const char *dflt)
{
char *message;
#if !defined(hpV4)
message = catgets(catd, set, num, dflt);
#else
_DtMsgCache *c;
char *message = NULL;
_DtMsgCache *c;
char **setptr;
int i, multiplier;
int size;
@@ -96,8 +98,6 @@ char *_DtCatgetsCached(nl_catd catd, int set, int num, char *dflt)
int setIdx = set - 1;
int numIdx = num - 1;
_DtSvcProcessLock();
c = get_msg_cache(catd);
if (NULL == c)
{
@@ -150,8 +150,32 @@ char *_DtCatgetsCached(nl_catd catd, int set, int num, char *dflt)
message = setptr[numIdx];
_DtSvcProcessUnlock();
#endif /* hpV4 */
return message;
}
#endif /* hpV4 */
int _DtCatclose(nl_catd catd)
{
return (catd == (nl_catd) -1) ? 0 : catclose(catd);
}
char *_DtCatgets(nl_catd catd, int set, int num, const char *dflt)
{
char *msg = NULL;
if (catd == (nl_catd) -1 || set < 0 || num < 0) {
/* Some catgets() implementations will fault if catd is invalid. */
msg = (char *) dflt;
} else {
/* Per POSIX, we cannot assume catgets() is thread-safe. */
_DtSvcProcessLock();
#if defined(hpV4) && !defined(NO_XLIB)
msg = _DtCatgetsCached(catd, set, num, dflt);
#else
msg = catgets(catd, set, num, dflt);
#endif /* hpV4 */
_DtSvcProcessUnlock();
}
return msg;
}