bottleneck testcase based on rubbos
[bottlenecks.git] / rubbos / app / httpd-2.0.64 / srclib / apr / misc / win32 / internal.c
1 /* Licensed to the Apache Software Foundation (ASF) under one or more
2  * contributor license agreements.  See the NOTICE file distributed with
3  * this work for additional information regarding copyright ownership.
4  * The ASF licenses this file to You under the Apache License, Version 2.0
5  * (the "License"); you may not use this file except in compliance with
6  * the License.  You may obtain a copy of the License at
7  *
8  *     http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 #include "apr_private.h"
18
19 #include "apr_arch_misc.h"
20 #include "apr_arch_file_io.h"
21 #include <crtdbg.h>
22 #include <assert.h>
23
24 /* This module is the source of -static- helper functions that are
25  * entirely internal to apr.  If the fn is exported - it does not
26  * belong here.
27  *
28  * Namespace decoration is still required to protect us from symbol
29  * clashes in static linkages.
30  */
31
32
33 /* Shared by apr_app.c and start.c 
34  *
35  * An internal apr function to convert an array of strings (either
36  * a counted or NULL terminated list, such as an argv[argc] or env[]
37  * list respectively) from wide Unicode strings to narrow utf-8 strings.
38  * These are allocated from the MSVCRT's _CRT_BLOCK to trick the system
39  * into trusting our store.
40  */
41 int apr_wastrtoastr(char const * const * *retarr, 
42                     wchar_t const * const *arr, int args)
43 {
44     apr_size_t elesize = 0;
45     char **newarr;
46     char *elements;
47     char *ele;
48     int arg;
49
50     if (args < 0) {
51         for (args = 0; arr[args]; ++args)
52             ;
53     }
54
55     newarr = _malloc_dbg((args + 1) * sizeof(char *),
56                          _CRT_BLOCK, __FILE__, __LINE__);
57
58     for (arg = 0; arg < args; ++arg) {
59         newarr[arg] = (void*)(wcslen(arr[arg]) + 1);
60         elesize += (apr_size_t)newarr[arg];
61     }
62
63     /* This is a safe max allocation, we will realloc after
64      * processing and return the excess to the free store.
65      * 3 ucs bytes hold any single wchar_t value (16 bits)
66      * 4 ucs bytes will hold a wchar_t pair value (20 bits)
67      */
68     elesize = elesize * 3 + 1;
69     ele = elements = _malloc_dbg(elesize * sizeof(char), 
70                                  _CRT_BLOCK, __FILE__, __LINE__);
71
72     for (arg = 0; arg < args; ++arg) {
73         apr_size_t len = (apr_size_t)newarr[arg];
74         apr_size_t newlen = elesize;
75
76         newarr[arg] = ele;
77         (void)apr_conv_ucs2_to_utf8(arr[arg], &len,
78                                     newarr[arg], &elesize);
79
80         newlen -= elesize;
81         ele += newlen;
82         assert(elesize && (len == 0));
83     }
84
85     newarr[arg] = NULL;
86     *(ele++) = '\0';
87
88     /* Return to the free store if the heap realloc is the least bit optimized
89      */
90     ele = _realloc_dbg(elements, ele - elements, 
91                        _CRT_BLOCK, __FILE__, __LINE__);
92
93     if (ele != elements) {
94         apr_size_t diff = ele - elements;
95         for (arg = 0; arg < args; ++arg) {
96             newarr[arg] += diff;
97         }
98     }
99
100     *retarr = newarr;
101     return args;
102 }