Nachinstallation von .Net 3.5

Die Installation von .NET 3.5 ist eine echte Herausforderung:
Trotz Internetanbindung schlägt das Nachladen meist fehl.

Die einfachste variante ist, meiner Meinung nach, das einlegend der DVD und dann die Offline-Installation per DISM:

DISM /Online /Enable-Feature /FeatureName:NetFx3 /All /LimitAccess /Source:f:\sources\sxs

Die Option „LimitAccess“ sorgt dafür, dass kein Kontakt zum Internet aufgenommen wird.

Der Pfad bei „Source“ muss mit dem korrekten Laufwerksbuchstaben versehen werden!

 

Exchange Monitoring (ver 1.2.2)

Einfaches Monitoring von einer Exchange-Umgebung ( Jetzt auch für Exhcange 2013/6 )

Folgendes wird überprüft:

  • Dienst die auf Automatisches Starten eingestellt sind
  • Festplatten (leerer Speicherplatz)
  • Queues
  • Clusterresourcen
    • Dieser Test wird nur noch durchgeführt, wenn die entsprechende Rolle auf dem lokalem System installiert ist.
  • Zertifikate (Ablaufdatum)

„Exchange Monitoring (ver 1.2.2)“ weiterlesen

Mailbox-Datenbank leer räumen

Es gibt unterschiedliche Szenarien in denen eine Datenbank ausgedient hat:

  • Volume ist voll
  • Änderung der Namenskonvention
  • Änderung der Struktur wie z.B. eine DB pro Abteilung oder Standort

Seit Exchange 2010 ist es auf alle Fälle möglich ein Postfach in eine andere Datenbank zu verschieben, ohne dass der Benutzer gestört wird.

Ein Verschieben der Datenbank ist ohne Down-Time nicht möglich. Daher empfehle stat desse nimmer eine neue DB zu erstellen und die Mailboxen zu verschieben.

Mit den folgenden 3 Zeilen PowerShell-Code werden alle Postfächer von einer DB in eine andere geschoben.

Das ganze ist als Beispiel gedacht!

Die alte DB heisst „Mailbox Database 1507976970“

Die neue DB hat den Namen „Mail-01“

Get-MailboxDatabase "Mailbox Database 1507976970" | Get-Mailbox | New-MoveRequest -TargetDatabase Mail-01
Get-MailboxDatabase "Mailbox Database 1507976970" | Get-Mailbox -Archiv | New-MoveRequest -TargetDatabase Mail-01
Get-MailboxDatabase "Mailbox Database 1507976970" | Get-Mailbox -Arbitration | New-MoveRequest -TargetDatabase Mail-01

 

 

WMI-Filter testen

In Gruppenrichtlinien kommen häufig WMI-Filter zum Einsatz.

Mit dem CMDlet Get-WMIObject kann man auf jedem PC, auf dem Power Shell läuft, die WMI-Filter testen. Am besten auf dem PC auf dem die Filter wirken sollen.

Hinweis: WMI-Filter von GPOs werden auf dem Client ausgeführt und das Ergebnis entscheidet ob die Richtlinie angewendet wird oder nicht.
WMI-Filter benötigen somit Ressourcen vom Client und der Server muss auf das Ergebnis warten. Wie immer gilt: Verwendung in maßen und nicht in Massen!

Hier ein Beispiel mit Ausgabe:

PS C:\Users\rob> Get-WmiObject -Query "select * from Win32_ComputerSystem where PCSystemType = 3"


Domain              : PowerShell.PUB
Manufacturer        : Gigabyte Technology Co., Ltd.
Model               : To be filled by O.E.M.
Name                : PC-1
PrimaryOwnerName    : administrator
TotalPhysicalMemory : 16999178240

Eine Ausgabe bedeutet TRUE und wenn nichts ausgegeben wurde ist das Ergebnis FALSE

Hier noch ein hilfreicher Link: https://technet.microsoft.com/en-us/library/jj717288.aspx

NTFS-Change Permissions

Die normalen Änderungsrechte auf ein Verzeichnis geben meist zu viele Rechte. Der Benutzer ist dadurch in der Lage das Verzeichnis zu löschen, umzubenennen oder zu verschieben.

Als Administrator möchte man das meist nicht und die Änderungen passiert meist auch nicht mit Absicht. Schnell die Maus über die Liste der Verzeichnisse bewegt und dabei versehentlich die linke Taste kurz ausgelöst. Schon ist ein Verzeichnis verschoben und es fällt erst mal nicht auf…

Die Rechte anzupassen ist dabei nicht Aufwendig:

  1. Eigenschaften des Verzeichnisses öffnen
  2. Den Tab „Sicherheit“ anklicken
  3. Auf den Button „Erweitert“ im Fenster unten rechts klicken
  4. Den betroffenen Benutzer oder Gruppe auswählen und auf „Ändern“ klicken
  5. Bei Windows 8 und 8.1 muss man nun noch den Link „Erweiterte Berechtigungen anzeigen“ anklicken
  6. Berechtigung wie im Bild vergeben. Markiert sind die Optionen die geändert wurden gegenüber den Änderungsrechten.

FolderPerm

 

…und dies wäre nicht „PowerShell.PUB“ wenn es kein Script dafür geben würde:

Wenn Sie auf das Verzeichnis C:\Daten folgende Rechte vergeben möchten:

  • Vollzugriff für SYSTEM
  • Vollzugriff für lokale Admins
  • Änderungsrechte für Benutzer (unterhalb des Verzeichnisses

Folgender Einzeiler erledigt das für Sie:

icacls c:\Daten /inheritance:r /grant *S-1-5-32-544:(OI)(CI)(F) /grant *S-1-5-18:(OI)(CI)(F) /grant *S-1-5-32-545:(OI)(CI)(RX,W,DC)

Es wir mit SIDs gearbeitet, da diese international funktionieren. Umlaute und andere Sonderzeichen erzeugen manchmal Probleme.

Lokales System: S-1-5-32-18
Lokaler Admin: S-1-5-32-544
Lokaler Benutzer: S-1-5-32-545

Die restlichen well known SIDs können Sie hier finden: https://support.microsoft.com/kb/243330

MAC-Authentifizierung

In manchen Fällen benötigt man Accounts für Netzwerkgeräte die per Radius (802.1x) im Netz authentifiziert werden sollen. Mit folgendem Skript können einzelne Geräte per Parameter oder mehrere per CSV-Datei erstellt werden.

#------------------------------------------------------------------------------#
# Skript zum erstellen von Accouts für Netzwerkgeräte die über den Radius per 
# MAC-Adresse authentifiziert werden müssen
# Autor: Rob   	        8.8.2013
#------------------------------------------------------------------------------#
# Changelog:
# Datum			Änderung
# 	
#------------------------------------------------------------------------------#
param
	(
	[string]$File,
	[string]$Name,
	[string]$MAC,
	[string]$OU="MACAUTH",
	[string]$DN="OU=Clients,DC=MyDomain,DC=Local",
	[string]$Gruppe="MACAUTH_CLIENT",
	[switch]$DEBUG
	)
#------------------------------------------------------------------------------#
# Die Datei muss ein CSV-File mit folgender Struktur sein:
#------------------------------------------------------------------------------#
# Name,MAC,OU,Gruppe
# Tel0005,081508150818,XYZ,MACAUTH_CLIENT
#------------------------------------------------------------------------------#
 
#region Script Diagnostic Functions 
 
function Get-CurrentLineNumber {
    $MyInvocation.ScriptLineNumber
}
 
New-Alias -Name __LINE__ -Value Get-CurrentLineNumber –Description ‘Returns the current line number in a PowerShell script file.‘
 
function Get-CurrentFileName {
    $MyInvocation.ScriptName
}
 
New-Alias -Name __FILE__ -Value Get-CurrentFileName -Description ‘Returns the name of the current PowerShell script file.‘
 
#endregion
 
 
 
$error.clear()	# Fehlerbehandlung
 
if ( $File -eq "" )	# Keine Datei Angegeeben
	{
	if ( $Debug ) { Write-host "No File" }
	if ( $MAC -eq "" -or $Name -eq "" ) # Beide müssen angegeben sein
		{
		Write-warning "$(__Line__): Es muss entweder eine Datei oder Name und MAC-Adresse angegeben werden!"
		exit
		}
	else	# MAC prüfen
		{
		$MAC = $MAC -replace "([^a-f0-9])"
		if ( $MAC.Length -ne 12 )
			{
			write-warning "$(__Line__): MAC Adresse ungültig bei $Name ( $MAC )"
			exit
			}
		}
	$Accounts = ""
	$Accounts = $Accounts | add-member -membertype noteproperty -name MAC -value $MAC -passthru
	$Accounts = $Accounts | add-member -membertype noteproperty -name Name -value $Name -passthru
	if ( $Gruppe -ne "" )
		{
		if ( $Debug ) { write-host "Gruppe per Komandozeile:" $Gruppe }
		$Accounts = $Accounts | add-member -membertype noteproperty -name Gruppe -value $Gruppe -passthru
		}
	}
else					# Datei angegeben
	{
	if ( $MAC -ne "" -or $Name -ne "" ) # Keiner darf angegeben sein
		{
		Write-warning "$(__Line__): Es muss entweder eine Datei oder Name und MAC-Adresse angegeben werden!"
		exit
		}
	if ( -not (test-path $file) )
		{
		write-warning "$(__Line__): Gültigen Dateinamen angeben!"
		exit
		}
	$TMP1 = get-content $file
	if ( $TMP1.count -lt 1 )
		{
		write-warning "$(__Line__): Die Datei ist leer oder nicht lesbar"
		exit
		}
	Remove-Item $file -force -confirm:$false
	foreach ( $TMP2 in $TMP1 )
		{
		$TMP2 = $TMP2.trim()
		if ( $TMP2.length -ne 0 )
			{
			$TMP2 | out-file -FilePath $file -Append
			}
		}
 
	$Accounts = import-csv $file -Delimiter "`t" | Select @{Name="Name";Expression={$_."Hostname"}}, @{Name="MAC";Expression={$_."MAC-Adresse"}}, @{Name="OU";Expression={$_."AD-OU"}}
	}
 
if ( $error.count -ne 0 )
	{
	write-warning "$(__Line__): Abbruch wegen Fehler!"
	exit
	}
 
foreach ( $Account in $Accounts )
	{
	$MAC = $Account.MAC -replace "([^a-f0-9])"
	$Name = $Account.Name
	if ( $Debug ) { write-host $Name `t $MAC }
	if ( $MAC.Length -ne 12 )
		{
 
		write-warning "$(__Line__): MAC Adresse ungültig bei $Name ( $MAC )"
		exit
		}
 
	$Probe = Get-ADUser -Filter { (SamAccountName -eq $MAC ) -or (Name -eq $Name) -or (DisplayName -eq $Name)}
	if (( $Probe | measure).count -ne 0 )
		{
		write-warning "$(__Line__): Ein Objekt mit dem Namen $Name oder $MAC existiert bereits!"
		if ( $file -ne "" ) { Write-warning "Es wurde kein neuer Account angelegt!" }
		write-host "Vorhandenes Objekt:" $Probe
		exit
		}
	}
 
foreach ( $Account in $Accounts )
	{
	$MAC = $Account.MAC.toupper() -replace "([^a-f0-9])"
	$Name = $Account.Name
	$PWD = ConvertTo-SecureString -String $MAC.tolower() -asplaintext -force
	if ( $Account.OU )
		{
		$MACDN = "OU=" + $Account.OU + "," + $DN
		}
	else
		{
		$MACDN = $DN
		}
	$Probe = ( Get-ADObject -Filter { ( DistinguishedName -eq $MACDN ) } )
	if ( ( $Probe | measure).count -eq 0 )
		{
		write-warning "$(__Line__): Der Distinguished Name ( $MACDN ) ist ungültig!"
		exit
		}
	$TMP1 = "OU=" + $OU + "," + $MACDN
	$Probe = ( Get-ADObject -Filter { ( DistinguishedName -eq $TMP1 ) } )
	if ( ( $Probe | measure).count -eq 0 )
		{
		New-ADOrganizationalUnit -Name $OU -Path $MACDN -ProtectedFromAccidentalDeletion $true -Description "Objekte die per MAC authentifiziert werden: Drucker oder Apple Mac"
		}
	$MACDN = $TMP1
	if ( $Debug ) { write-host "DN:" $MACDN }
	if ( $error.count -ne 0 )
		{
		write-warning "$(__Line__): Abbruch wegen Fehler!"
		exit
		}
 
	New-ADuser -Enabled $true -PasswordNeverExpires $true -AllowReversiblePasswordEncryption $true -CannotChangePassword $true -Path $MACDN -SamAccountName $MAC -DisplayName $Name -Name $Name -AccountPassword $PWD
	$MACDN = ( Get-ADUser $MAC ).DistinguishedName
	if ( $error.count -ne 0 )
		{
		write-warning "$(__Line__): Abbruch wegen Fehler!"
		write-warning "Accout: $MAC `t DN: $MACDN"
		exit
		}
 
	if ( -not $Gruppe )
		{
		$Gruppe = $Account.Gruppe
		}
	if ( $Debug ) { write-host "Gruppe:" $Gruppe }
	$SID = (((Get-ADGroup $Gruppe).SID).Value.tostring())
	$SID = $SID.substring($SID.LastIndexOf("-")+1)
	if ( $Debug ) { write-host $Gruppe `t $SID }
	if ( $error.count -ne 0 )
		{
		write-warning "$(__Line__): Abbruch wegen Fehler!"
		exit
		}
	Add-ADGroupMember $Gruppe $MAC
	Set-ADObject -Identity $MACDN -Replace @{primaryGroupID="$SID"}
 
	sleep 1
	Remove-ADGroupmember "Domänen-Benutzer" -Member $MAC -confirm:$false
 
	if ( $error.count -ne 0 )
		{
		write-warning "$(__Line__): Abbruch wegen Fehler!"
		exit
		}
	}

 

Zertifikate nach PEM (ascii) konvertieren

Zertifikate aus einer Windows Zertifizierungsstelle die mit privatem Schlüssel exportiert werden, sind im pkcs12 Format. Mit hilfe von OPENSSL kann man den Privaten Schlüssel und der Zertifikat exportieren (d.h. jeweils in eine Datei speichern) und in das PEM-Format konvertieren:

Export private Key: openssl pkcs12 -in windows-cert.pfx -out priv-key.pem -nodes -nocerts

Export certificate: openssl pkcs12 -in windows-cert.pfx -out cert.pem -nodes -nokeys

SAN-Zertifikate von eigener CA

SAN-Zertifikate
Um Zertifikate zu erstellen die für mehrere Namen gültig sind, muß man die Zertifikatsstelle dafür konfigurieren. Das geht mit folgender Befehlsfolge:

certutil -setreg policy\EditFlags +EDITF_ATTRIBUTESUBJECTALTNAME2
net stop certsvc
net start certsvc

Bei dem Request muß dann im Feld Attribute die Namesliste angegeben werden:

SAN:dns=servername.mydomain.com&dns=servername&dns=phones&dns=phones.mydomain.com

WINSXS verkleinern

Bei den aktuellen Betriebssystemen von Microsoft wurde das Patchmanagemen etwas verändert. Unter Windows XP wurden die Unsinstall-FIles unter c:\Windows abgelegt. Diese konnten meist einfach gelöscht werden da die Updates meist gar nicht deinstallierbar waren. Ab Vista wurde das WINSXS-Verzeichnis eingeführt. Hier werden Versions-Historien geführt. Dies kann und sollte man nicht einfach löschen! Mit Vista will ich mich auf dieser Seite nicht beschäftigen… Das WINSXS-Verzeichnis wird auf Dauer ziemlich groß und kann somit durchaus ein anfangs großzügig ausgelegtes C: zum überlaufen bringen 🙁

Mit folgendem Befehl kann mann zumindest Dateien löschen lassen, die Seit SP1 überflüssig geworden sind. Dies habe ich unter Windos 7 und Windows 2008 R2 erfolgreich durchgeführt.

dism /online /cleanup-image /spsuperseded

Quelle: How to reclaim space after applying Windows 7/2008 R2 Service Pack 1

NTP Einstellungen

Bei Windows 2000 können Sie einfach mit NET TIME die IP-Adresse des Servers angeben. Führen Sie in einer DOS-Box dazu folgende Befehle aus:

net stop w32time
net time /setsntp:xxx.xxx.xxx.xxx
net start w32time
w32tm.exe /once

Seit Windows 2003 hat sich der Aufruf der Konfiguration geändert.

w32tm /config /syncfromflags:manual /manualpeerlist:time.firma.tld /update /reliable:YES

Diese Zeile setzt den Zeitserver auf „Manuelles Update“ von „time.firma.tld“ und gibt sich dann als „zuverlässiger“ Zeitserver aus und holt sich sofort die Zeit. Seit Windows 2003 ist es auch möglich, ein Debuglog für den W32TIME-Dienst zu aktivieren. Speichern Sie einfach folgende Zeilen als REG-Datei und importieren Sie diese

Windows Registry Editor Version 5.00
 
[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\W32Time\Config]
"FileLogName"="c:\\temp\\ntp.log"
"FileLogSize"=dword:01000000
"FileLogEntries"="0-116"

Vergessen Sie am Ende nicht, das Diagnoseprotokoll wieder abzuschalten. Bei Windows 2000 können Sie die „w32tm /once“ eine interaktive Verbindung zum NTP-Server in der Konsole beobachten. Auch im Systemeventlog hinterlässt W32TIME entsprechende Meldungen, wenn ein Fehler auftritt.

Autoritativer Zeitserver Wenn es nun keinem ihrer Domänencontroller möglich ist, eine Zeit von einer vertrauenswürdigen NTP-Quelle zu bekommen, dann sollten Sie natürlich einen DC zur maßgeblich Zeitquelle deklarieren und dort sicherstellen, dass dessen Uhrzeit möglichst genau geht. Dies könnte dann eine Hardwareuhr (DCF77 o.ä.) sein, die einfach die lokale Uhr immer wieder korrigiert.

Um einen Windows Server nun zu einer „Referenz“ zu deklarieren, müssen Sie per Regedit zwei Schlüssel setzen. Speichern Sie einfach diesen text z.B. als „W32HWTime.reg und importieren diesen auf dem PDC-Emulator der Stammdomäne

Windows Registry Editor Version 5.00
 
[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\W32Time\Parameters]
"LocalNTP"=dword:00000001
"ReliableTimeSource"=dword:00000001

Danach müssen Sie den Windows Zeitdienst einmal durchstarten (net stop w32time && net start w32time). Sorgen Sie dann noch dafür, dass alle Clients und anderen Server die Zeit neu holen (z.B.: durch Eingabe von „w32tm -s“ und kontrollieren Sie das Eventlog.

216734 How to configure an authoritative time server in Windows 2000

So konfigurieren Sie den Windows-Zeitdienst auf dem ersten Controller in der Gesamtstruktur-Stammdomäne

  1. Melden Sie sich beim ersten Domänencontroller an, den Sie bereitgestellt haben.
  2. Geben Sie an einer Eingabeaufforderung den folgenden Befehl ein, und drücken Sie dann die EINGABETASTE:
    w32tm /stripchart /computer:de.pool.ntp.org /samples:5 /dataonly

    Dadurch wird getestet, ob eine Verbindung zu einem Timeserver im Internet möglich ist.

  3. Öffnen Sie bei Bedarf den UDP-Port (User Datagram Protocol) 123 für ausgehenden Datenverkehr ins Internet.
  4. Öffnen Sie den UDP-Port 123 für eingehenden NTP-Datenverkehr am PDC-Emulator (Windows-Firewall).
  5. Geben Sie zum Konfigurieren des PDC-Emulators den folgenden Befehl ein, und drücken Sie dann die EINGABETASTE:
    w32tm /config /manualpeerlist:<Peers> /syncfromflags:manual /reliable:yes /update

Parameter Beschreibung

W32tm /stripchart Zeigt ein Diagramm des Offsets zwischen synchronisierenden Computern an.

W32tm /config /update Konfiguriert den PDC-Emulator.

/computer:<Ziel> Gibt den DNS-Namen (Domain Name System) oder die IP-Adresse des NTP-Servers an, dessen Zeit mit der Zeit auf dem lokalen Computer verglichen werden soll. Ein Beispiel für einen NTP-Server ist time.windows.com.

/samples:<Anzahl> Gibt die Anzahl der vom Zielcomputer zurückgegebenen Zeitbeispiele an.

/dataonly Gibt an, dass in den Ergebnissen nur Daten, aber keine Grafiken angezeigt werden.

/manualpeerlist:<Peers> Listet die DNS-Namen oder IP-Adressen für die NTP-Zeitquelle auf, mit denen der PDC-Emulator synchronisiert wird. (Diese Liste wird als manuelle Peerliste bezeichnet.) Sie können beispielsweise time.windows.com als NTP-Zeitserver angeben. Verwenden Sie beim Angeben mehrerer Peers ein Leerzeichen als Trennzeichen, und schließen Sie die Namen der Peers in Anführungszeichen ein.

/syncfromflags:manual Gibt an, dass die Zeit mit Peers in der manuellen Peerliste synchronisiert werden soll.

/reliable:yes Gibt an, dass es sich bei dem Computer um einen zuverlässigen Zeitdienst handelt.