mirror of
https://gitlab.winehq.org/wine/wine-staging.git
synced 2025-01-28 22:04:43 -08:00
Added vbscript_join patchset
This commit is contained in:
parent
e452a6cbdc
commit
93f5b4f6a0
267
patches/vbscript_join/0001-vbscript-implement-Join.patch
Normal file
267
patches/vbscript_join/0001-vbscript-implement-Join.patch
Normal file
@ -0,0 +1,267 @@
|
||||
From 83867c594f2114dd6f8ea76d12e1a2134a417962 Mon Sep 17 00:00:00 2001
|
||||
From: Francis De Brabandere <francisdb@gmail.com>
|
||||
Date: Fri, 20 Dec 2024 17:02:19 +0100
|
||||
Subject: [PATCH] vbscript: implement Join()
|
||||
|
||||
---
|
||||
dlls/vbscript/global.c | 129 +++++++++++++++++++++++++++++++++++-
|
||||
dlls/vbscript/tests/api.vbs | 95 ++++++++++++++++++++++++++
|
||||
2 files changed, 221 insertions(+), 3 deletions(-)
|
||||
|
||||
diff --git a/dlls/vbscript/global.c b/dlls/vbscript/global.c
|
||||
index 972d0d2ea0b..10d5709e73c 100644
|
||||
--- a/dlls/vbscript/global.c
|
||||
+++ b/dlls/vbscript/global.c
|
||||
@@ -2581,10 +2581,133 @@ static HRESULT Global_Filter(BuiltinDisp *This, VARIANT *arg, unsigned args_cnt,
|
||||
return E_NOTIMPL;
|
||||
}
|
||||
|
||||
-static HRESULT Global_Join(BuiltinDisp *This, VARIANT *arg, unsigned args_cnt, VARIANT *res)
|
||||
+static HRESULT Global_Join(BuiltinDisp *This, VARIANT *args, unsigned args_cnt, VARIANT *res)
|
||||
{
|
||||
- FIXME("\n");
|
||||
- return E_NOTIMPL;
|
||||
+ BSTR delimiter = NULL, output = NULL, str = NULL;
|
||||
+ BOOL free_delimiter = FALSE;
|
||||
+ SAFEARRAY *sa;
|
||||
+ HRESULT hres;
|
||||
+ LONG lbound, ubound;
|
||||
+ VARIANT *data;
|
||||
+ UINT total_len = 0, delimiter_len = 0, str_len;
|
||||
+ WCHAR *output_ptr;
|
||||
+ INT i;
|
||||
+
|
||||
+ assert(1 <= args_cnt && args_cnt <= 2);
|
||||
+
|
||||
+ switch(V_VT(args)) {
|
||||
+ case VT_NULL:
|
||||
+ return MAKE_VBSERROR(VBSE_ILLEGAL_NULL_USE);
|
||||
+ case VT_DISPATCH:
|
||||
+ return MAKE_VBSERROR(VBSE_OLE_NO_PROP_OR_METHOD);
|
||||
+ case VT_VARIANT|VT_ARRAY:
|
||||
+ sa = V_ARRAY(args);
|
||||
+ break;
|
||||
+ case VT_VARIANT|VT_ARRAY|VT_BYREF:
|
||||
+ sa = *V_ARRAYREF(args);
|
||||
+ break;
|
||||
+ default:
|
||||
+ return MAKE_VBSERROR(VBSE_TYPE_MISMATCH);
|
||||
+ }
|
||||
+
|
||||
+ if (args_cnt == 2) {
|
||||
+ if (V_VT(args + 1) == VT_NULL)
|
||||
+ return MAKE_VBSERROR(VBSE_ILLEGAL_NULL_USE);
|
||||
+ if (V_VT(args + 1) != VT_BSTR) {
|
||||
+ hres = to_string(args + 1, &delimiter);
|
||||
+ if (FAILED(hres))
|
||||
+ return hres;
|
||||
+ } else {
|
||||
+ delimiter = V_BSTR(args + 1);
|
||||
+ }
|
||||
+ } else {
|
||||
+ delimiter = SysAllocString(L" ");
|
||||
+ if (!delimiter)
|
||||
+ return E_OUTOFMEMORY;
|
||||
+ free_delimiter = TRUE;
|
||||
+ }
|
||||
+
|
||||
+ if (SafeArrayGetDim(sa) != 1) {
|
||||
+ hres = MAKE_VBSERROR(VBSE_TYPE_MISMATCH);
|
||||
+ goto cleanup;
|
||||
+ }
|
||||
+
|
||||
+ hres = SafeArrayGetLBound(sa, 1, &lbound);
|
||||
+ if (FAILED(hres))
|
||||
+ goto cleanup;
|
||||
+
|
||||
+ hres = SafeArrayGetUBound(sa, 1, &ubound);
|
||||
+ if (FAILED(hres))
|
||||
+ goto cleanup;
|
||||
+
|
||||
+ hres = SafeArrayAccessData(sa, (void**)&data);
|
||||
+ if (FAILED(hres))
|
||||
+ goto cleanup;
|
||||
+
|
||||
+ delimiter_len = SysStringLen(delimiter);
|
||||
+
|
||||
+ for (i = lbound; i <= ubound; i++) {
|
||||
+ if (V_VT(&data[i]) != VT_BSTR) {
|
||||
+ hres = to_string(&data[i], &str);
|
||||
+ if (FAILED(hres))
|
||||
+ goto cleanup_data;
|
||||
+ } else {
|
||||
+ str = V_BSTR(&data[i]);
|
||||
+ }
|
||||
+
|
||||
+ total_len += SysStringLen(str);
|
||||
+ if (i > lbound)
|
||||
+ total_len += delimiter_len;
|
||||
+
|
||||
+ if (V_VT(&data[i]) != VT_BSTR)
|
||||
+ SysFreeString(str);
|
||||
+ }
|
||||
+
|
||||
+ output = SysAllocStringLen(NULL, total_len);
|
||||
+ if (!output) {
|
||||
+ hres = E_OUTOFMEMORY;
|
||||
+ goto cleanup_data;
|
||||
+ }
|
||||
+
|
||||
+ output_ptr = output;
|
||||
+
|
||||
+ for (i = lbound; i <= ubound; i++) {
|
||||
+ if (V_VT(&data[i]) != VT_BSTR) {
|
||||
+ hres = to_string(&data[i], &str);
|
||||
+ if (FAILED(hres))
|
||||
+ goto cleanup_output;
|
||||
+ } else {
|
||||
+ str = V_BSTR(&data[i]);
|
||||
+ }
|
||||
+
|
||||
+ if (i > lbound) {
|
||||
+ memcpy(output_ptr, delimiter, delimiter_len * sizeof(WCHAR));
|
||||
+ output_ptr += delimiter_len;
|
||||
+ }
|
||||
+
|
||||
+ str_len = SysStringLen(str);
|
||||
+ memcpy(output_ptr, str, str_len * sizeof(WCHAR));
|
||||
+ output_ptr += str_len;
|
||||
+
|
||||
+ if (V_VT(&data[i]) != VT_BSTR)
|
||||
+ SysFreeString(str);
|
||||
+ }
|
||||
+
|
||||
+ *output_ptr = L'\0';
|
||||
+ SafeArrayUnaccessData(sa);
|
||||
+ if (free_delimiter)
|
||||
+ SysFreeString(delimiter);
|
||||
+
|
||||
+ return return_bstr(res, output);
|
||||
+
|
||||
+cleanup_output:
|
||||
+ SysFreeString(output);
|
||||
+cleanup_data:
|
||||
+ SafeArrayUnaccessData(sa);
|
||||
+cleanup:
|
||||
+ if (free_delimiter)
|
||||
+ SysFreeString(delimiter);
|
||||
+ return hres;
|
||||
}
|
||||
|
||||
static HRESULT Global_Split(BuiltinDisp *This, VARIANT *args, unsigned args_cnt, VARIANT *res)
|
||||
diff --git a/dlls/vbscript/tests/api.vbs b/dlls/vbscript/tests/api.vbs
|
||||
index dfa2816bec5..7a27912279a 100644
|
||||
--- a/dlls/vbscript/tests/api.vbs
|
||||
+++ b/dlls/vbscript/tests/api.vbs
|
||||
@@ -22,6 +22,45 @@ Dim x
|
||||
Class EmptyClass
|
||||
End Class
|
||||
|
||||
+' Returns the amount of dimensions of an array.
|
||||
+' Returns 0 when it is not an array
|
||||
+Function GetDimensions(arr)
|
||||
+ Dim dimension, upperBound
|
||||
+ On error resume next
|
||||
+ For dimension = 1 to 255
|
||||
+ upperBound = ubound(arr, dimension)
|
||||
+ If err.Number <> 0 Then Exit for
|
||||
+ Next
|
||||
+ On error goto 0
|
||||
+ GetDimensions = dimension-1
|
||||
+End Function
|
||||
+
|
||||
+' Helper function to print a variable
|
||||
+Function ToString(x)
|
||||
+ If IsEmpty(x) Then
|
||||
+ ToString = "Empty"
|
||||
+ ElseIf IsNull(x) Then
|
||||
+ ToString = "Null"
|
||||
+ ElseIf IsObject(x) Then
|
||||
+ ToString = "Object"
|
||||
+ ElseIf IsArray(x) Then
|
||||
+ Dim i, arrStr
|
||||
+ arrStr = "Array("
|
||||
+ If GetDimensions(x) = 1 Then
|
||||
+ For i = LBound(x) To UBound(x)
|
||||
+ arrStr = arrStr & ToString(x(i))
|
||||
+ If i < UBound(x) Then arrStr = arrStr & ", "
|
||||
+ Next
|
||||
+ Else
|
||||
+ arrStr = arrStr & "...multidim..."
|
||||
+ End If
|
||||
+ arrStr = arrStr & ")"
|
||||
+ ToString = arrStr
|
||||
+ Else
|
||||
+ ToString = CStr(x)
|
||||
+ End If
|
||||
+End Function
|
||||
+
|
||||
Call ok(vbSunday = 1, "vbSunday = " & vbSunday)
|
||||
Call ok(getVT(vbSunday) = "VT_I2", "getVT(vbSunday) = " & getVT(vbSunday))
|
||||
Call ok(vbMonday = 2, "vbMonday = " & vbMonday)
|
||||
@@ -713,6 +752,62 @@ TestLCase 0.123, doubleAsString(0.123)
|
||||
TestLCase Empty, ""
|
||||
Call ok(getVT(LCase(Null)) = "VT_NULL", "getVT(LCase(Null)) = " & getVT(LCase(Null)))
|
||||
|
||||
+' Join
|
||||
+
|
||||
+Sub TestJoin(arg, ex)
|
||||
+ x = Join(arg)
|
||||
+ Call ok(x = ex, "Join(" & ToString(arg) & ") = " & x & " expected " & ex)
|
||||
+End Sub
|
||||
+
|
||||
+Sub TestJoin2(arg1, arg2, ex)
|
||||
+ x = Join(arg1, arg2)
|
||||
+ Call ok(x = ex, "Join(" & ToString(arg1) & "," & arg2 & ") = " & x & " expected " & ex)
|
||||
+End Sub
|
||||
+
|
||||
+Sub TestJoinError(arg, num)
|
||||
+ On Error Resume Next
|
||||
+ Call Join(arg)
|
||||
+ Dim err_num: err_num = Err.number
|
||||
+ Call Err.clear()
|
||||
+ On Error GoTo 0
|
||||
+ Call ok(err_num = num, "Join(" & ToString(arg) & ") expected Err.number = " & num & " got " & err_num)
|
||||
+End Sub
|
||||
+
|
||||
+TestJoin Array(), ""
|
||||
+TestJoin Array("a", "b", "c"), "a b c"
|
||||
+TestJoin Array("a", "b", "c", 1, 2, 3), "a b c 1 2 3"
|
||||
+TestJoin Array(1, Empty), "1 "
|
||||
+
|
||||
+TestJoin2 Array(), "", ""
|
||||
+TestJoin2 Array("a"), "-", "a"
|
||||
+TestJoin2 Array("a", "b"), "-", "a-b"
|
||||
+TestJoin2 Array("a", "b", "c"), "", "abc"
|
||||
+TestJoin2 Array(1, "Hello"), "-", "1-Hello"
|
||||
+TestJoin2 Array("a", "b", "c"), Empty, "abc"
|
||||
+
|
||||
+TestJoinError Null , 94
|
||||
+TestJoinError Empty, 13
|
||||
+TestJoinError 1, 13
|
||||
+TestJoinError "test", 13
|
||||
+TestJoinError 1.2, 13
|
||||
+TestJoinError New EmptyClass, 438
|
||||
+TestJoinError Array(1, Null), 13
|
||||
+TestJoinError Array(Array(1, 2), Array(3, 4)), 13
|
||||
+Dim multidim(2, 2)
|
||||
+TestJoinError multidim, 13
|
||||
+
|
||||
+On Error Resume Next
|
||||
+Call Join(Array(), Null)
|
||||
+Call ok(Err.number = 94, "Join(Array(), Null) expected Err.number = 94 got " & Err.number)
|
||||
+Call Err.clear
|
||||
+On Error GoTo 0
|
||||
+
|
||||
+On Error Resume Next
|
||||
+Call Join(Array(), "a", "b")
|
||||
+Call ok(Err.number = 450, "Join(Array(), ""a"", ""b"") expected Err.number = 450 got " & Err.number)
|
||||
+Call Err.clear
|
||||
+On Error GoTo 0
|
||||
+
|
||||
x=Split("abc")
|
||||
Call ok(x(0) = "abc", "Split(""abc"")(0)=" & x(0))
|
||||
x = Split("abc def")
|
||||
--
|
||||
2.45.2
|
||||
|
3
patches/vbscript_join/definition
Normal file
3
patches/vbscript_join/definition
Normal file
@ -0,0 +1,3 @@
|
||||
Fixes: [56464] vbscript: Implement Join
|
||||
|
||||
# MR https://gitlab.winehq.org/wine/wine/-/merge_requests/7052
|
Loading…
x
Reference in New Issue
Block a user