Architettura dei sistemi Windows

Enrico Lodolo

e.lodolo@bo.nettuno.it

Inquadramento storico

La famiglia WinXX

Architettura: API e DLL

Architettura: driver e sottosistemi

Architettura: DLL

DLL: caricamento statico e dinamico

Confronto: shared objects

Architettura: modello ad eventi

Architettura: messaggi e finestre

Architettura Windows: callback

Modello ad eventi e multitasking

Risorse

Hello Windows: struttura

Hello Windows - 1

#include <windows.h>

long __stdcall WndProc(HWND, UINT, WPARAM, LPARAM);
int __stdcall WinMain(HANDLE hInstance, HANDLE hPrevInstance,
LPSTR lpszCmdParam, int nCmdShow)
{
static char zsAppName[] = "HelloWin";
HWND hwnd;
MSG msg;
WNDCLASS wndclass;

wndclass.style = CS_REDRAW | CS_VREDRAW;
wndclass.lpfnWndProc = WndProc;
wndclass.cbClsExtra = 0;
wndclass.cbWndExtra = 0;
wndclass.hInstance = hInstance;
wndclass.hIcon = LoadIcon(NULL, IDI_APPLICATION);
wndclass.hCursor = LoadCursor(NULL, IDC_ARROW);
wndclass.hbrBackground = (HBRUSH) GetStockObject(WHITE_BRUSH);
wndclass.lpszMenuName = NULL;
wndclass.lpszClassName = szAppName;
RegisterClass(&wndclass);

Hello Windows - 2

hwnd = CreateWindow(szAppName, // window class name
"The Hello Program", // window caption
WS_OVERLAPPEDWINDOW, // window style
CW_USEDEFAULT, // initial x position
CW_USEDEFAULT, // initial y position
CW_USEDEFAULT, // initial x size
CW_USEDEFAULT, // initial y size
NULL, // parent window handdle
NULL, // window menu handle
hInstance, // program instance handle
NULL);

ShowWndow(hwnd, nCmdShow);
UpdateWindow(hwnd);
while (GetMessage(&msg, NULL, 0, 0))
{
TranslateMessage(&msg)
DispatchMessage(&msg)
}
return msg.wParam;
}

Hello Windows - 3

long __stdcall WndProc(HWND hwnd, UINT iMsg, WPARAM wParam, LPARAM lParam)
{
HDC hdc;
PAINTSTRUCT ps;
RECT rect;
switch (iMsg)
{
case WM_PAINT:
hdc = BeginPaint(hwnd, &ps);
GetClientRect(hwnd, &rect);

DrawText(hdc, "Hello, Windows 95!", -1, &rect,
DT_SINGLELINE | DT_CENTER | DT_VCENTER);
EndPaint(hwnd, &ps);
return 0;
case WM_DESTROY:
PostQuitMessage(0);
return 0;
}
return DefWindowProc( hwnd, iMsg, wParam, lparam);
}

Esempi

hellobtn

case WM_CREATE :
CreateWindow("button", "Push",
WS_CHILD | WS_VISIBLE | BS_PUSHBUTTON, 10, 10, 60, 30, hwnd, (LPVOID)101,
hCurInstance, NULL);
return 0 ;
case WM_COMMAND:
if (wParam=101)
MessageBox(hwnd,"Pushed!","HelloBtn Message",MB_OK | MB_ICONEXCLAMATION);
return 0;
lcc -c -Ic:\lcc\include -g2 hellobtn.c
lcclnk -subsystem windows -o hellobtn.exe hellobtn.obj

testdll

#include <windows.h>
int _stdcall MyLibMain(void *hinstDll,unsigned long dwReason,void *reserved)
{
return(1);
}
void Popup(HWND hwnd)
{
MessageBox(hwnd,"Pushed!","Message from DLL",MB_OK | MB_ICONEXCLAMATION);
}

exports Popup

lcc -O -g2 testdll.c
lcclnk.exe -dll -entry MyLibMain testdll.obj testdll.def
implib testdll.dll

hellodll

case WM_COMMAND:
if (wParam=101)
Popup(hwnd);
return 0 ;

implib testdll.dll

lcc -c -Ic:\lcc\include -g2 hellodll.c
lcclnk -subsystem windows -o hellodll.exe hellodll.obj testdll.lib

hellodl2

FARPROC lpfnPopup; /* FARPROC è definito in windows.h */
void DoPopup(HWND hwnd)
{
HANDLE hDLL;
hDLL = LoadLibrary("TESTDLL.DLL"); /* carica la DLL (se non è già caricata) */
if (hDLL)
{
lpfnPopup=GetProcAddress(hDLL,"_Popup"); /* aggancia la funzione esportata */
(* lpfnPopup)(hwnd); /* chiama la funzione */
FreeLibrary(hDLL); /* scarica la DLL (se nessun altro la usa) */
}
}
case WM_COMMAND:
if (wParam=101)
DoPopup(hwnd);
return 0;
lcc -c -Ic:\lcc\include -g2 hellodl2.c
lcclnk -subsystem windows -o hellodl2.exe hellodl2.obj

Confronto: un’ applicazione GTK

#include <gtkgtk.h>
int main(int argc, char *argv[])
{
gtk_init(&argc, &argv);
GtkWidget *window = gtk_window_new(GTK_WINDOW_TOPLEVEL):
gtk_window_set_default_size(GTK_WINDOW(window), 100, 100);
gtk_widget_show(window);

gtk_main();
return(0);
}

Confronto: GTK e i segnali

#include <gtkgtk.h>
gint hello(GtkWidget *widget)
{
printf("hello!\n");
}
int main(int argc, char *argv[])
{
  gtk_init(&argc, &argv);
  GtkWidget *window = gtk_window_new(GTK_WINDOW_TOPLEVEL):
  GtkWidget *button = gtk_button_new_with_label("Hello!");
  gtk_container_add(GTK_CONTAINER(window), button);
  gtk_signal_connect(GTK_OBJECT(button), "clicked", GTK_SIGNAL_FUNCTION(hello), NULL);
  gtk_window_set_default_size(GTK_WINDOW(window), 100, 100);
  gtk_widget_show(button);
  gtk_widget_show(window);

  gtk_main();
  return(0);
}

Da Win16 a Win32: standard e common controls

Da Win16 a Win32: UI objects e kernel objects

Caratteristiche dei kernel objects

Processi e thread

Strumenti di sincronizzazione

Mutex e semafori

Oggetti stream

Oggetti stream - I/O sincrono e asincrono