Domanda

Ho un filtro ISAPI che gira su IIS6 o 7. Quando ci sono più processi di lavoro ( "Web garden"), il filtro verrà caricato ed eseguito in ogni w3wp.exe.

Come posso efficientemente consentire il filtro per accedere le proprie attività in un unico file di registro consolidato?

  • i messaggi di log dei diversi processi (concorrenti) non devono interferire con l'altro. In altre parole, un singolo messaggio di log emessa da una qualsiasi delle w3wp.exe deve essere realizzato come una singola linea contigua nel file di registro.

  • ci dovrebbe essere contesa minimo per il file di log. I siti possono servire 100 di richieste al secondo.

  • rigoroso ordine di tempo è preferito. In altre parole, se il processo w3wp.exe # 1 emette un messaggio a T1, allora il processo # 2 emette un messaggio in t2, allora il processo # 1 emette un messaggio al T3, i messaggi devono apparire in buone condizioni di tempo nel file di registro.

L'approccio attuale che ho è che ogni processo possiede un file di log separato. Questo ha ovvi inconvenienti.

Alcune idee:

  • nominare uno dei w3wp.exe di essere "proprietario del file di log" e inviare tutti i messaggi di log attraverso quel processo speciale. Questo ha problemi in caso di riciclo del processo di lavoro.

  • utilizzare un mutex sistema operativo per proteggere l'accesso al file di log. È questa alta perf abbastanza? In questo caso ogni w3wp.exe avrebbe un FILE sullo stesso file system. Devo fflush file di log dopo ogni scrittura? Sarà questo lavoro?

qualche suggerimento?

È stato utile?

Soluzione

In un primo momento stavo per dire che mi piace il tuo attuale approccio migliore, perché ogni processo azioni niente, e poi mi sono reso conto, che, beh, sono probabilmente tutti condividono lo stesso disco rigido sotto. Quindi, c'è ancora un collo di bottiglia in cui si verifica contesa. O forse i controllori del sistema operativo e il disco rigido sono veramente intelligenti sulla gestione di questo?

Credo che ciò che si vuole fare è avere la scrittura del log non rallentare i fili che stanno facendo il vero lavoro.

Quindi, eseguire un altro processo sulla stessa macchina (priorità più bassa?), Che scrive in realtà i messaggi di log su disco. Comunicare per l'altro processo utilizzando non UDP come suggerito, ma piuttosto la memoria che la quota di processi. Conosciuto anche, confusamente, come memoria per i file mappato. Di più su file mappati in memoria . Alla mia azienda, abbiamo trovato file mappati in memoria di essere molto più veloce di TCP loopback / IP per la comunicazione sulla stessa macchina, in modo da sto supponendo che sarebbe stato più veloce di UDP troppo.

Quello che effettivamente avete nella vostra memoria condivisa potrebbe essere, per cominciare, uno std :: coda dove i pushs e pop sono protetti utilizzando un mutex. Le discussioni che ISAPI avrebbero afferrare il mutex per mettere le cose nella coda. Il processo di registrazione dovrebbe prendere il mutex per tirare le cose fuori della coda, rilasciare il mutex, e poi scrivere le voci su disco. Il mutex è protetto solo l'aggiornamento della memoria condivisa, non è l'aggiornamento del file, così sembra, in teoria, che il mutex sarebbe tenuto per un tempo più breve, creando meno di un collo di bottiglia.

Il processo di registrazione potrebbe anche ri-organizzare l'ordine di ciò che sta scrivendo per ottenere i timestamp in ordine.

Ecco un'altra variazione: Contine di avere un registro separato per ogni processo, ma hanno un filo logger all'interno di ogni processo in modo che il filo tempi critici principale non deve aspettare che la registrazione avvenga al fine di procedere con la sua lavoro.

Il problema con tutto quello che ho scritto qui è che l'intero sistema - hardware, sistema operativo, il modo in cui multicore CPU L1 / L2 opere di cache, il software - è troppo complesso per essere facilmente prevedibile da un solo pensando che attraverso. CODICE alcune semplici applicazioni proof-of-concept, strumento li con alcuni tempi, e provarli sul hardware reale.

Altri suggerimenti

Sarebbe la registrazione in un database di senso make qui?

Ho usato un sistema di registrazione basato su UDP in passato e sono stato felice con questo tipo di soluzione.

I tronchi vengono inviati tramite UDP a un processo di log-collector che il suo compito di salvare in un file su base regolare.

Non so se può funzionare nel vostro contesto di alta perf ma ero soddisfatto di questa soluzione in una domanda ai sensi meno stress.

Spero che aiuta.

Invece di un Mutex sistema operativo per controllare l'accesso al file, si potrebbe utilizzare meccanismi di locking dei file Win32 con LockFile () e UnlockFile ().

Il mio suggerimento è di inviare messaggi in modo asincrono (UDP) per un processo che si farà carico di registrare il log.
Il processo:
- un ricevitore filo mette i messaggi in una coda;
- un thread è responsabile per la rimozione dei messaggi dalla coda mettere in un tempo lista ordinata;
- Un thread messaggi monitor nell'elenco e solo i messaggi con lunghezza di tempo superiore al minimo devono essere salvate nel file (per evitare che un messaggio in ritardo per essere scritto fuori uso)

.

Si potrebbe continuare la registrazione per separare i file e trovare / scrivere uno strumento per unire in un secondo momento (forse automatizzato, o si può solo funzionare in corrispondenza del punto che si desidera utilizzare i file.)

Event Tracing for Windows , incluso in Windows Vista e versioni successive, fornisce una bella capacità di questo.

Estratto:

  

Event Tracing for Windows (ETW) è un sistema di tracciamento a livello di kernel efficiente che consente di log del kernel o di eventi definiti dall'applicazione ad un file di log. Si può consumare gli eventi in tempo reale o da un file di log e li usa per eseguire il debug di un'applicazione o per determinare dove i problemi di prestazioni si verificano nell'applicazione.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top