Можно добавить отделение с runat = "сервер" к странице:
<div runat="server" id="myDiv">
</div>
и затем набор его свойство InnerHtml от кода - позади:
myDiv.InnerHtml = "your html here";
, Если Вы хотите изменить содержание DIV на стороне клиента, тогда можно использовать код JavaScript, подобный этому:
<script type="text/javascript">
Sys.Application.add_load(MyLoad);
function MyLoad(sender) {
$get('<%= div.ClientID %>').innerHTML += " - text added on client";
}
</script>
Да, программа может открывать один и тот же файл несколько раз из разных потоков. Однако вам следует избегать чтения из файла одновременно с записью в него. Вы можете использовать TMultiReadExclusiveWriteSynchronizer
для управления доступом ко всему файлу. Он менее сериализован, чем, скажем, критическая секция. Для более детального контроля взгляните на LockFileEx
, чтобы управлять доступом к определенным областям файла по мере необходимости. При записи запросить эксклюзивную блокировку; при чтении - разделяемая блокировка.
Что касается опубликованного вами кода, указание File_Share_Write
в начальных флагах совместного использования означает, что все последующие операции открытия также должны совместно использовать файл для записи. Цитата из документации :
Если этот флаг не указан, но файл или устройство были открыты для доступа на запись или имеют отображение файла с доступом на запись, функция не работает.
Ваш второй запрос на открытие говорил, что он не хочет, чтобы кому-либо было разрешено писать в файл, пока это ручка оставалась открытой. Поскольку уже был открыт другой дескриптор, который разрешил запись, второй запрос не мог быть выполнен. GetLastError
должен был вернуть 32, то есть Error_Sharing_Violation
, именно то, что должно произойти в документации.
Указание File_Flag_Delete_On_Close
означает, что все последующие открытые запросы должны совместно использовать файл для удаления. Снова документация:
Последующие запросы на открытие файла завершаются ошибкой, если не указан режим общего доступа
FILE_SHARE_DELETE
.
Затем, поскольку второй открытый запрос разделяет файл для удаления, все другие открытые дескрипторы также должны совместно использовать его для удаления. Документация:
Если существуют открытые дескрипторы файла, вызов завершится ошибкой, если все они не были открыты в режиме общего доступа
FILE_SHARE_DELETE
.
Суть в том, что либо все имеют одинаковый доступ, либо никто
FFileSystem := CreateFile(PChar(FFileName),
Generic_Read or Generic_Write
File_Share_Read or File_Share_Write or File_Share_Delete,
nil,
Create_Always,
File_Attribute_Normal or File_Flag_Random_Access
or File_Attribute_Temporary or File_Flag_Delete_On_Close,
0);
FFileSystem2 := CreateFile(PChar(FFileName),
Generic_Read,
File_Share_Read or File_Share_Write or File_Share_Delete,
nil,
Open_Existing,
File_Attribute_Normal or File_Flag_Random_Access
or File_Attribute_Temporary or File_Flag_Delete_On_Close,
0);
Другими словами, все параметры одинаковы, за исключением пятого.
Эти правила применяются к двум попыткам открытия в одном и том же потоке, а также попыткам из разных темы.
Вы можете сделать так ...
Первый поток с доступом для чтения / записи должен сначала создать файл:
FileHandle := CreateFile(
PChar(FileName),
GENERIC_READ or GENERIC_WRITE,
FILE_SHARE_READ,
nil,
CREATE_ALWAYS,
FILE_ATTRIBUTE_NORMAL,
0);
Второй поток с доступом только для чтения, затем открывает тот же файл:
FileHandle := CreateFile(
PCHar(FileName),
GENERIC_READ,
FILE_SHARE_READ + FILE_SHARE_WRITE,
nil,
OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL,
0);
Я не проверял, работает ли с ...
FILE_ATTRIBUTE_TEMPORARY,
FILE_FLAG_DELETE_ON_CLOSE
атрибутами ...
Мне нужно получить доступ к файлу одновременно с несколькими потоками. Это нужно делать одновременно, без сериализации потоков по соображениям производительности.
Либо вам не нужно использовать один и тот же файл в разных потоках, либо вам нужна какая-то сериализация.
В противном случае вы просто готовясь к душевной боли в будущем.
Я написал несколько тестовых проектов на C, чтобы попытаться понять это, хотя Роб Кеннеди опередил меня, пока я был в отъезде. Оба условия возможны, включая перекрестный процесс, как он подчеркивает. Вот ссылка, если кто-то еще хотел бы увидеть это в действии.
SharedFileTests.zip (VS2005 C ++ Solution) @ meklarian.com
Есть три проекта:
InProcessThreadShareTest - Тестирование создателя и клиентского потока.
SharedFileClient - создайте клиента, который работает в течение 30 секунд и опрашивает файл.
SharedFileHost.cpp и SharedFileClient.cpp Snippet @ gist.github
Все эти проекты предполагают расположение C: \ data \ tmp \ sharetest.txt можно создавать и записывать.
Судя по вашему сценарию, вам нужен очень большой кусок памяти. Вместо того, чтобы играть в системный кеш, вы можете использовать AWE для доступа к более чем 4 ГБ памяти, хотя вам нужно будет отображать части за раз. Это должно охватывать ваш сценарий L2, поскольку вы хотите убедиться, что используется физическая память.
Address Windowing Extensions @ MSDN
Используйте AllocateUserPhysicalPages и VirtualAlloc для резервирования памяти.
Функция AllocateUserPhysicalPages (Windows) @ MSDN
Функция VirtualAlloc (Windows) @ MSDN
Учитывая, что вы используете флаг FILE_FLAG_DELETE_ON_CLOSE, есть ли причина, по которой вы не стали бы использовать отображение памяти? файл?
Управление файлами с отображением памяти в Win32 @ MSDN
Из того, что я вижу в ваших инструкциях CreateFile, похоже, что вы хотите обмениваться данными между потоками или между процессами, имея в виду только одинаковые файл присутствует, пока открыты все сеансы. Файл с отображением памяти позволяет использовать одно и то же логическое имя файла во всех сеансах. Еще одно преимущество заключается в том, что вы можете отображать представления и блокировать части сопоставленного файла с безопасностью во всех сеансах. Если у вас есть строгий сервер со сценарием с N-клиентом, это должно быть легко реализовать. Если у вас есть случай, когда любой клиент может быть открывающим сервером, вы можете рассмотреть возможность использования какого-либо другого механизма, чтобы гарантировать, что только один клиент сможет сначала инициировать обслуживающий файл (возможно, через глобальный мьютекс).
Если вам нужна только односторонняя передача данных, возможно, вы могли бы использовать вместо этого именованные каналы.
(edit) Это лучше всего для 1 сервера на 1 клиента.