Imported Upstream version 0.6.3
[fdkaac.git] / src / compat_win32.c
CommitLineData
48e2f01c 1/*
2 * Copyright (C) 2013 nu774
3 * For conditions of distribution and use, see copyright notice in COPYING
4 */
5#if HAVE_CONFIG_H
6# include "config.h"
7#endif
8#if HAVE_STDINT_H
9# include <stdint.h>
10#endif
11#include <stdio.h>
12#include <stdlib.h>
13#include <string.h>
14#include <stdarg.h>
dac71de3 15#include <assert.h>
48e2f01c 16#include <io.h>
17#include <fcntl.h>
7ce09815 18#include <share.h>
48e2f01c 19#include <sys/timeb.h>
20#include "compat.h"
21#define WIN32_LEAN_AND_MEAN
22#include <windows.h>
9b7e1ca6 23#include <shellapi.h>
48e2f01c 24
25int64_t aacenc_timer(void)
26{
ffc230a8 27#if HAVE_STRUCT___TIMEB64
48e2f01c 28 struct __timeb64 tv;
29 _ftime64(&tv);
bd02d0e7 30#else
31 struct timeb tv;
32 ftime(&tv);
33#endif
48e2f01c 34 return (int64_t)tv.time * 1000 + tv.millitm;
35}
36
9b7e1ca6
MG
37int aacenc_seekable(FILE *fp)
38{
39 return GetFileType((HANDLE)_get_osfhandle(_fileno(fp))) == FILE_TYPE_DISK;
40}
41
48e2f01c 42static
43int codepage_decode_wchar(int codepage, const char *from, wchar_t **to)
44{
45 int nc = MultiByteToWideChar(codepage, 0, from, -1, 0, 0);
46 if (nc == 0)
47 return -1;
48 *to = malloc(nc * sizeof(wchar_t));
49 MultiByteToWideChar(codepage, 0, from, -1, *to, nc);
50 return 0;
51}
52
53static
54int codepage_encode_wchar(int codepage, const wchar_t *from, char **to)
55{
56 int nc = WideCharToMultiByte(codepage, 0, from, -1, 0, 0, 0, 0);
57 if (nc == 0)
58 return -1;
59 *to = malloc(nc);
60 WideCharToMultiByte(codepage, 0, from, -1, *to, nc, 0, 0);
61 return 0;
62}
63
64FILE *aacenc_fopen(const char *name, const char *mode)
65{
66 wchar_t *wname, *wmode;
67 FILE *fp;
68
69 if (strcmp(name, "-") == 0) {
70 fp = (mode[0] == 'r') ? stdin : stdout;
71 _setmode(_fileno(fp), _O_BINARY);
72 } else {
7ce09815 73 int share = _SH_DENYRW;
74 if (strchr(mode, 'r') && !strchr(mode, '+'))
75 share = _SH_DENYWR;
48e2f01c 76 codepage_decode_wchar(CP_UTF8, name, &wname);
77 codepage_decode_wchar(CP_UTF8, mode, &wmode);
7ce09815 78 fp = _wfsopen(wname, wmode, share);
48e2f01c 79 free(wname);
80 free(wmode);
81 }
82 return fp;
83}
84
bfb6aa3c 85static char **__aacenc_argv__;
86
87static
88void aacenc_free_mainargs(void)
89{
90 char **p = __aacenc_argv__;
91 for (; *p; ++p)
7b1f2136 92 free(*p);
bfb6aa3c 93 free(__aacenc_argv__);
94}
95
48e2f01c 96void aacenc_getmainargs(int *argc, char ***argv)
97{
98 int i;
9b7e1ca6 99 wchar_t **wargv;
48e2f01c 100
9b7e1ca6 101 wargv = CommandLineToArgvW(GetCommandLineW(), argc);
48e2f01c 102 *argv = malloc((*argc + 1) * sizeof(char*));
103 for (i = 0; i < *argc; ++i)
104 codepage_encode_wchar(CP_UTF8, wargv[i], &(*argv)[i]);
9b7e1ca6 105 LocalFree(wargv);
48e2f01c 106 (*argv)[*argc] = 0;
bfb6aa3c 107 __aacenc_argv__ = *argv;
108 atexit(aacenc_free_mainargs);
48e2f01c 109}
110
111char *aacenc_to_utf8(const char *s)
112{
113 return _strdup(s);
114}
115
dac71de3 116#if defined(__MINGW32__) && !defined(HAVE__VSCPRINTF)
117int _vscprintf(const char *fmt, va_list ap)
118{
119 static int (*fp_vscprintf)(const char *, va_list) = 0;
120 if (!fp_vscprintf) {
121 HANDLE h = GetModuleHandleA("msvcrt.dll");
122 FARPROC fp = GetProcAddress(h, "_vscprintf");
123 InterlockedCompareExchangePointer(&fp_vscprintf, fp, 0);
124 }
125 assert(fp_vscprintf);
126 return fp_vscprintf(fmt, ap);
127}
128#endif
129
48e2f01c 130int aacenc_fprintf(FILE *fp, const char *fmt, ...)
131{
132 va_list ap;
133 int cnt;
134 HANDLE fh = (HANDLE)_get_osfhandle(_fileno(fp));
135
136 if (GetFileType(fh) != FILE_TYPE_CHAR) {
137 va_start(ap, fmt);
138 cnt = vfprintf(fp, fmt, ap);
139 va_end(ap);
140 } else {
141 char *s;
142 wchar_t *ws;
143 DWORD nw;
144
145 va_start(ap, fmt);
146 cnt = _vscprintf(fmt, ap);
147 va_end(ap);
148
149 s = malloc(cnt + 1);
150
151 va_start(ap, fmt);
152 cnt = _vsnprintf(s, cnt + 1, fmt, ap);
153 va_end(ap);
154
155 codepage_decode_wchar(CP_UTF8, s, &ws);
156 free(s);
157 fflush(fp);
a79a11ef 158 WriteConsoleW(fh, ws, wcslen(ws), &nw, 0);
48e2f01c 159 free(ws);
160 }
161 return cnt;
162}
163
5888fddc 164const char *aacenc_basename(const char *path)
165{
166/*
167 * Since path is encoded with UTF-8, naive usage of strrchr() shoule be safe.
168 */
169 const char *p = strrchr(path, '/');
170 const char *q = strrchr(path, '\\');
171 const char *r = strrchr(path, ':');
172 if (q > p) p = q;
173 if (r > p) p = r;
174 return p ? p + 1 : path;
175}
This page took 0.021572 seconds and 4 git commands to generate.