В этом нет ничего специфичного для Скалы. Это просто вопрос того, что целевой тип присваивания не имеет отношения к типу, в котором выполняется операция (в данном случае умножение).
Например, в C #:
using System;
class Program
{
static void Main(string[] args)
{
int a = unchecked(86400000 * 150);
long b = unchecked(86400000 * 150);
long c = 86400000 * (long) 150;
long d = 86400000 * 150L;
Console.WriteLine(a); // 75098112
Console.WriteLine(b); // 75098112
Console.WriteLine(c); // 12960000000
Console.WriteLine(d); // 12960000000
}
}
Часть unchecked
здесь заключается в том, что компилятор C # достаточно умен, чтобы понимать, что операция переполняется, но только потому, что оба операнда являются константами. Если бы любой операнд был переменной, все было бы хорошо без unchecked
.
Аналогично в Java:
public class Program
{
public static void main(String[] args)
{
int a = 86400000 * 150;
long b = 86400000 * 150;
long c = 86400000 * (long) 150;
long d = 86400000 * 150L;
System.out.println(a); // 75098112
System.out.println(b); // 75098112
System.out.println(c); // 12960000000
System.out.println(d); // 12960000000
}
}
Самый простой способ - заставить вашу службу создать общую память и указать DACL в CreateFileMapping, который предоставляет обычным пользователям доступ для чтения к общей памяти.
Обычные пользователи не имеют создать глобальную привилегию, но службы могут иметь эту привилегию. Если вам нужно, чтобы ваши пользователи создавали общую память, а затем проверяли ее службой, у вас может быть схема IPC, в которой ваш пользовательский код отправляет сообщение службе, содержащей дескриптор сопоставления файлов, а затем служба будет вызывать DuplicateHandle для получения ссылка на него. Это потребует, чтобы ваша служба запускалась с привилегией отладки.
Самый простой способ создать DACL - использовать ConvertStringSecurityDescriptorToSecurityDescriptor, который принимает строку в формате SDDL, определяющую ACL.
Написание безопасного кода содержит отличную главу о создании DACL с помощью SDDL.
// Error handling removed for brevity
SECURITY_ATTRIBUTES attributes;
ZeroMemory(&attributes, sizeof(attributes));
attributes.nLength = sizeof(attributes);
ConvertStringSecurityDescriptorToSecurityDescriptor(
L"D:P(A;OICI;GA;;;SY)(A;OICI;GA;;;BA)(A;OICI;GR;;;IU)",
SDDL_REVISION_1,
&attributes.lpSecurityDescriptor,
NULL);
CreateFileMapping(INVALID_HANDLE_VALUE, &attributes,
PAGE_READWRITE, sizeHigh, sizeLow, L"Global\\MyObject");
LocalFree(attributes.lpSecurityDescriptor);
«D: P (A; OICI; GA ;;; SY) (A; OICI; GA ;;; BA) (A ; OICI; GR ;;; IU) "определяет DACL. D: P означает, что это DACL (вместо SACL ... вы редко используете SACL), за которым следуют несколько строк ACE, которые контролируют, кто получает доступ. Каждый из них - A (разрешить), разрешает объект и содержит наследование (OICI). Первым, кто предоставит полный доступ (GA - предоставить все) Системе (SY) и администраторам (BA, встроенным администраторам). Последний предоставляет чтение (GR) интерактивным пользователям (IU), которые являются пользователями, фактически вошедшими в сеанс.
Как только это будет сделано, обычные пользователи смогут вызвать OpenFileMapping, чтобы получить дескриптор общего сопоставления, и уметь отображать это в своем процессе. Поскольку обычные пользователи имеют ограниченные права на объект, они ' обязательно откройте его и сопоставьте только для чтения.
Если пользователям требуется доступ для записи, вы должны заменить GR на GWGR. Обратите внимание, что это небезопасно - ограниченный пользователь сможет изменить общую память, пока ваша служба читает и пытается проанализировать информацию, что приведет к сбою вашей службы.