1103856Stjr/*-
2103856Stjr * Copyright (c) 1990, 1993
3103856Stjr *	The Regents of the University of California.  All rights reserved.
4103856Stjr *
5103856Stjr * This code is derived from software contributed to Berkeley by
6103856Stjr * Donn Seeley at UUNET Technologies, Inc.
7103856Stjr *
8227753Stheraven * Copyright (c) 2011 The FreeBSD Foundation
9227753Stheraven * All rights reserved.
10227753Stheraven * Portions of this software were developed by David Chisnall
11227753Stheraven * under sponsorship from the FreeBSD Foundation.
12227753Stheraven *
13103856Stjr * Redistribution and use in source and binary forms, with or without
14103856Stjr * modification, are permitted provided that the following conditions
15103856Stjr * are met:
16103856Stjr * 1. Redistributions of source code must retain the above copyright
17103856Stjr *    notice, this list of conditions and the following disclaimer.
18103856Stjr * 2. Redistributions in binary form must reproduce the above copyright
19103856Stjr *    notice, this list of conditions and the following disclaimer in the
20103856Stjr *    documentation and/or other materials provided with the distribution.
21249808Semaste * 3. Neither the name of the University nor the names of its contributors
22103856Stjr *    may be used to endorse or promote products derived from this software
23103856Stjr *    without specific prior written permission.
24103856Stjr *
25103856Stjr * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
26103856Stjr * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
27103856Stjr * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
28103856Stjr * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
29103856Stjr * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
30103856Stjr * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
31103856Stjr * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
32103856Stjr * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
33103856Stjr * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
34103856Stjr * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
35103856Stjr * SUCH DAMAGE.
36103856Stjr */
37103856Stjr
38103856Stjr#include <sys/cdefs.h>
39103856Stjr#if 0
40103856Stjr#if defined(LIBC_SCCS) && !defined(lint)
41103856Stjrstatic char sccsid[] = "@(#)vsscanf.c	8.1 (Berkeley) 6/4/93";
42103856Stjr#endif /* LIBC_SCCS and not lint */
43103856Stjr__FBSDID("FreeBSD: src/lib/libc/stdio/vsscanf.c,v 1.11 2002/08/21 16:19:57 mike Exp ");
44103856Stjr#endif
45103856Stjr__FBSDID("$FreeBSD$");
46103856Stjr
47103856Stjr#include <limits.h>
48103856Stjr#include <stdarg.h>
49103856Stjr#include <stdio.h>
50103856Stjr#include <stdlib.h>
51103856Stjr#include <string.h>
52103856Stjr#include <wchar.h>
53103856Stjr#include "local.h"
54227753Stheraven#include "xlocale_private.h"
55103856Stjr
56103856Stjrstatic int	eofread(void *, char *, int);
57103856Stjr
58103856Stjrstatic int
59103856Stjreofread(void *cookie, char *buf, int len)
60103856Stjr{
61103856Stjr
62103856Stjr	return (0);
63103856Stjr}
64103856Stjr
65103856Stjrint
66227753Stheravenvswscanf_l(const wchar_t * __restrict str, locale_t locale,
67227753Stheraven		const wchar_t * __restrict fmt, va_list ap)
68103856Stjr{
69128002Stjr	static const mbstate_t initial;
70128002Stjr	mbstate_t mbs;
71205021Sjhb	FILE f = FAKE_FILE;
72103856Stjr	char *mbstr;
73103856Stjr	size_t mlen;
74103856Stjr	int r;
75187302Srdivacky	const wchar_t *strp;
76227753Stheraven	FIX_LOCALE(locale);
77103856Stjr
78103856Stjr	/*
79103856Stjr	 * XXX Convert the wide character string to multibyte, which
80103856Stjr	 * __vfwscanf() will convert back to wide characters.
81103856Stjr	 */
82103856Stjr	if ((mbstr = malloc(wcslen(str) * MB_CUR_MAX + 1)) == NULL)
83103856Stjr		return (EOF);
84128002Stjr	mbs = initial;
85187302Srdivacky	strp = str;
86227753Stheraven	if ((mlen = wcsrtombs_l(mbstr, &strp, SIZE_T_MAX, &mbs, locale)) == (size_t)-1) {
87103856Stjr		free(mbstr);
88103856Stjr		return (EOF);
89103856Stjr	}
90103856Stjr	f._flags = __SRD;
91103856Stjr	f._bf._base = f._p = (unsigned char *)mbstr;
92103856Stjr	f._bf._size = f._r = mlen;
93103856Stjr	f._read = eofread;
94227753Stheraven	r = __vfwscanf(&f, locale, fmt, ap);
95103856Stjr	free(mbstr);
96103856Stjr
97103856Stjr	return (r);
98103856Stjr}
99227753Stheravenint
100227753Stheravenvswscanf(const wchar_t * __restrict str, const wchar_t * __restrict fmt,
101227753Stheraven    va_list ap)
102227753Stheraven{
103227753Stheraven	return vswscanf_l(str, __get_locale(), fmt, ap);
104227753Stheraven}
105