1e1051a39Sopenharmony_ci/* 2e1051a39Sopenharmony_ci * Copyright 2010-2016 The OpenSSL Project Authors. All Rights Reserved. 3e1051a39Sopenharmony_ci * 4e1051a39Sopenharmony_ci * Licensed under the Apache License 2.0 (the "License"). You may not use 5e1051a39Sopenharmony_ci * this file except in compliance with the License. You can obtain a copy 6e1051a39Sopenharmony_ci * in the file LICENSE in the source distribution or at 7e1051a39Sopenharmony_ci * https://www.openssl.org/source/license.html 8e1051a39Sopenharmony_ci */ 9e1051a39Sopenharmony_ci 10e1051a39Sopenharmony_ci#if defined( __VMS) && !defined( OPENSSL_NO_DECC_INIT) && \ 11e1051a39Sopenharmony_ci defined( __DECC) && !defined( __VAX) && (__CRTL_VER >= 70301000) 12e1051a39Sopenharmony_ci# define USE_DECC_INIT 1 13e1051a39Sopenharmony_ci#endif 14e1051a39Sopenharmony_ci 15e1051a39Sopenharmony_ci#ifdef USE_DECC_INIT 16e1051a39Sopenharmony_ci 17e1051a39Sopenharmony_ci/* 18e1051a39Sopenharmony_ci * ---------------------------------------------------------------------- 19e1051a39Sopenharmony_ci * decc_init() On non-VAX systems, uses LIB$INITIALIZE to set a collection 20e1051a39Sopenharmony_ci * of C RTL features without using the DECC$* logical name method. 21e1051a39Sopenharmony_ci * ---------------------------------------------------------------------- 22e1051a39Sopenharmony_ci */ 23e1051a39Sopenharmony_ci 24e1051a39Sopenharmony_ci# include <stdio.h> 25e1051a39Sopenharmony_ci# include <stdlib.h> 26e1051a39Sopenharmony_ci# include <unixlib.h> 27e1051a39Sopenharmony_ci 28e1051a39Sopenharmony_ci/* Global storage. */ 29e1051a39Sopenharmony_ci 30e1051a39Sopenharmony_ci/* Flag to sense if decc_init() was called. */ 31e1051a39Sopenharmony_ci 32e1051a39Sopenharmony_ciint decc_init_done = -1; 33e1051a39Sopenharmony_ci 34e1051a39Sopenharmony_ci/* Structure to hold a DECC$* feature name and its desired value. */ 35e1051a39Sopenharmony_ci 36e1051a39Sopenharmony_citypedef struct { 37e1051a39Sopenharmony_ci char *name; 38e1051a39Sopenharmony_ci int value; 39e1051a39Sopenharmony_ci} decc_feat_t; 40e1051a39Sopenharmony_ci 41e1051a39Sopenharmony_ci/* 42e1051a39Sopenharmony_ci * Array of DECC$* feature names and their desired values. Note: 43e1051a39Sopenharmony_ci * DECC$ARGV_PARSE_STYLE is the urgent one. 44e1051a39Sopenharmony_ci */ 45e1051a39Sopenharmony_ci 46e1051a39Sopenharmony_cidecc_feat_t decc_feat_array[] = { 47e1051a39Sopenharmony_ci /* Preserve command-line case with SET PROCESS/PARSE_STYLE=EXTENDED */ 48e1051a39Sopenharmony_ci {"DECC$ARGV_PARSE_STYLE", 1}, 49e1051a39Sopenharmony_ci 50e1051a39Sopenharmony_ci /* Preserve case for file names on ODS5 disks. */ 51e1051a39Sopenharmony_ci {"DECC$EFS_CASE_PRESERVE", 1}, 52e1051a39Sopenharmony_ci 53e1051a39Sopenharmony_ci /* 54e1051a39Sopenharmony_ci * Enable multiple dots (and most characters) in ODS5 file names, while 55e1051a39Sopenharmony_ci * preserving VMS-ness of ";version". 56e1051a39Sopenharmony_ci */ 57e1051a39Sopenharmony_ci {"DECC$EFS_CHARSET", 1}, 58e1051a39Sopenharmony_ci 59e1051a39Sopenharmony_ci /* List terminator. */ 60e1051a39Sopenharmony_ci {(char *)NULL, 0} 61e1051a39Sopenharmony_ci}; 62e1051a39Sopenharmony_ci 63e1051a39Sopenharmony_ci 64e1051a39Sopenharmony_ci/* LIB$INITIALIZE initialization function. */ 65e1051a39Sopenharmony_ci 66e1051a39Sopenharmony_cistatic void decc_init(void) 67e1051a39Sopenharmony_ci{ 68e1051a39Sopenharmony_ci char *openssl_debug_decc_init; 69e1051a39Sopenharmony_ci int verbose = 0; 70e1051a39Sopenharmony_ci int feat_index; 71e1051a39Sopenharmony_ci int feat_value; 72e1051a39Sopenharmony_ci int feat_value_max; 73e1051a39Sopenharmony_ci int feat_value_min; 74e1051a39Sopenharmony_ci int i; 75e1051a39Sopenharmony_ci int sts; 76e1051a39Sopenharmony_ci 77e1051a39Sopenharmony_ci /* Get debug option. */ 78e1051a39Sopenharmony_ci openssl_debug_decc_init = getenv("OPENSSL_DEBUG_DECC_INIT"); 79e1051a39Sopenharmony_ci if (openssl_debug_decc_init != NULL) { 80e1051a39Sopenharmony_ci verbose = strtol(openssl_debug_decc_init, NULL, 10); 81e1051a39Sopenharmony_ci if (verbose <= 0) { 82e1051a39Sopenharmony_ci verbose = 1; 83e1051a39Sopenharmony_ci } 84e1051a39Sopenharmony_ci } 85e1051a39Sopenharmony_ci 86e1051a39Sopenharmony_ci /* Set the global flag to indicate that LIB$INITIALIZE worked. */ 87e1051a39Sopenharmony_ci decc_init_done = 1; 88e1051a39Sopenharmony_ci 89e1051a39Sopenharmony_ci /* Loop through all items in the decc_feat_array[]. */ 90e1051a39Sopenharmony_ci 91e1051a39Sopenharmony_ci for (i = 0; decc_feat_array[i].name != NULL; i++) { 92e1051a39Sopenharmony_ci /* Get the feature index. */ 93e1051a39Sopenharmony_ci feat_index = decc$feature_get_index(decc_feat_array[i].name); 94e1051a39Sopenharmony_ci if (feat_index >= 0) { 95e1051a39Sopenharmony_ci /* Valid item. Collect its properties. */ 96e1051a39Sopenharmony_ci feat_value = decc$feature_get_value(feat_index, 1); 97e1051a39Sopenharmony_ci feat_value_min = decc$feature_get_value(feat_index, 2); 98e1051a39Sopenharmony_ci feat_value_max = decc$feature_get_value(feat_index, 3); 99e1051a39Sopenharmony_ci 100e1051a39Sopenharmony_ci /* Check the validity of our desired value. */ 101e1051a39Sopenharmony_ci if ((decc_feat_array[i].value >= feat_value_min) && 102e1051a39Sopenharmony_ci (decc_feat_array[i].value <= feat_value_max)) { 103e1051a39Sopenharmony_ci /* Valid value. Set it if necessary. */ 104e1051a39Sopenharmony_ci if (feat_value != decc_feat_array[i].value) { 105e1051a39Sopenharmony_ci sts = decc$feature_set_value(feat_index, 106e1051a39Sopenharmony_ci 1, decc_feat_array[i].value); 107e1051a39Sopenharmony_ci 108e1051a39Sopenharmony_ci if (verbose > 1) { 109e1051a39Sopenharmony_ci fprintf(stderr, " %s = %d, sts = %d.\n", 110e1051a39Sopenharmony_ci decc_feat_array[i].name, 111e1051a39Sopenharmony_ci decc_feat_array[i].value, sts); 112e1051a39Sopenharmony_ci } 113e1051a39Sopenharmony_ci } 114e1051a39Sopenharmony_ci } else { 115e1051a39Sopenharmony_ci /* Invalid DECC feature value. */ 116e1051a39Sopenharmony_ci fprintf(stderr, 117e1051a39Sopenharmony_ci " INVALID DECC$FEATURE VALUE, %d: %d <= %s <= %d.\n", 118e1051a39Sopenharmony_ci feat_value, 119e1051a39Sopenharmony_ci feat_value_min, decc_feat_array[i].name, 120e1051a39Sopenharmony_ci feat_value_max); 121e1051a39Sopenharmony_ci } 122e1051a39Sopenharmony_ci } else { 123e1051a39Sopenharmony_ci /* Invalid DECC feature name. */ 124e1051a39Sopenharmony_ci fprintf(stderr, 125e1051a39Sopenharmony_ci " UNKNOWN DECC$FEATURE: %s.\n", decc_feat_array[i].name); 126e1051a39Sopenharmony_ci } 127e1051a39Sopenharmony_ci } 128e1051a39Sopenharmony_ci 129e1051a39Sopenharmony_ci if (verbose > 0) { 130e1051a39Sopenharmony_ci fprintf(stderr, " DECC_INIT complete.\n"); 131e1051a39Sopenharmony_ci } 132e1051a39Sopenharmony_ci} 133e1051a39Sopenharmony_ci 134e1051a39Sopenharmony_ci/* Get "decc_init()" into a valid, loaded LIB$INITIALIZE PSECT. */ 135e1051a39Sopenharmony_ci 136e1051a39Sopenharmony_ci# pragma nostandard 137e1051a39Sopenharmony_ci 138e1051a39Sopenharmony_ci/* 139e1051a39Sopenharmony_ci * Establish the LIB$INITIALIZE PSECTs, with proper alignment and other 140e1051a39Sopenharmony_ci * attributes. Note that "nopic" is significant only on VAX. 141e1051a39Sopenharmony_ci */ 142e1051a39Sopenharmony_ci# pragma extern_model save 143e1051a39Sopenharmony_ci 144e1051a39Sopenharmony_ci# if __INITIAL_POINTER_SIZE == 64 145e1051a39Sopenharmony_ci# define PSECT_ALIGN 3 146e1051a39Sopenharmony_ci# else 147e1051a39Sopenharmony_ci# define PSECT_ALIGN 2 148e1051a39Sopenharmony_ci# endif 149e1051a39Sopenharmony_ci 150e1051a39Sopenharmony_ci# pragma extern_model strict_refdef "LIB$INITIALIZ" PSECT_ALIGN, nopic, nowrt 151e1051a39Sopenharmony_ciconst int spare[8] = { 0 }; 152e1051a39Sopenharmony_ci 153e1051a39Sopenharmony_ci# pragma extern_model strict_refdef "LIB$INITIALIZE" PSECT_ALIGN, nopic, nowrt 154e1051a39Sopenharmony_civoid (*const x_decc_init) () = decc_init; 155e1051a39Sopenharmony_ci 156e1051a39Sopenharmony_ci# pragma extern_model restore 157e1051a39Sopenharmony_ci 158e1051a39Sopenharmony_ci/* Fake reference to ensure loading the LIB$INITIALIZE PSECT. */ 159e1051a39Sopenharmony_ci 160e1051a39Sopenharmony_ci# pragma extern_model save 161e1051a39Sopenharmony_ci 162e1051a39Sopenharmony_ciint LIB$INITIALIZE(void); 163e1051a39Sopenharmony_ci 164e1051a39Sopenharmony_ci# pragma extern_model strict_refdef 165e1051a39Sopenharmony_ciint dmy_lib$initialize = (int)LIB$INITIALIZE; 166e1051a39Sopenharmony_ci 167e1051a39Sopenharmony_ci# pragma extern_model restore 168e1051a39Sopenharmony_ci 169e1051a39Sopenharmony_ci# pragma standard 170e1051a39Sopenharmony_ci 171e1051a39Sopenharmony_ci#else /* def USE_DECC_INIT */ 172e1051a39Sopenharmony_ci 173e1051a39Sopenharmony_ci/* Dummy code to avoid a %CC-W-EMPTYFILE complaint. */ 174e1051a39Sopenharmony_ciint decc_init_dummy(void); 175e1051a39Sopenharmony_ci 176e1051a39Sopenharmony_ci#endif /* def USE_DECC_INIT */ 177