Instalações silenciosas via GPO às vezes falham com rollback e o erro 1376 (“o grupo local especificado não existe”). Este guia explica por que isso acontece, como encontrar o grupo faltante no log do MSI e como corrigir de forma robusta com GPP, gMSA e boas práticas.
Contexto e sintomas
O cenário típico é o seguinte: uma Diretiva de Grupo de Computador (GPO, em Computer Configuration → Policies → Windows Settings → Scripts → Startup) executa um .cmd
que chama um instalador .msi
. A chamada adiciona parâmetros, incluindo credenciais de domínio para configurar o serviço criado pelo instalador. O pacote está publicado em \<domínio>\NETLOGON
. A instalação começa, o software chega a ser copiado, mas quando o serviço vai iniciar ou quando o instalador tenta aplicar permissões, ocorre rollback. No log em C:\Windows\Temp
surge: “A system error 1376 occurred. The specified local group does not exist.”
Esse padrão normalmente vem acompanhado de Event IDs do MsiInstaller no Visualizador de Eventos e, em instalações silenciosas (/qn
), aparece apenas um genérico 1603
na saída, enquanto a causa-raiz real é o 1376
dentro do log detalhado do MSI.
Entendendo o erro 1376
O código 1376, traduzido, é “o grupo local especificado não existe”. Em termos práticos, significa que o instalador ou um script de suporte tentou:
- Adicionar uma conta (de serviço, por exemplo) a um grupo local que não existe na máquina-alvo;
- Aplicar permissões/ACL (LockPermissions) a um grupo local inexistente;
- Consultar membros de um grupo local que ainda não foi criado ou cujo nome difere do esperado (localização/idioma).
Por que “funciona manualmente” e falha via GPO? O contexto de execução é diferente:
- Startup Script roda como LocalSystem, antes do logon do usuário, quando nem tudo no ambiente (rede, DFS, resolução de nomes, política aplicada) está pronto;
- Executando manualmente você já tem rede estável, cache de credenciais, resolução de grupos e, muitas vezes, privilégios/traduções de nomes resolvidos;
- Em SOs localizados, o instalador pode estar procurando o nome inglês de um grupo embutido (ex.: “Performance Log Users”) enquanto o sistema exibe nomes traduzidos. Referências por nome são frágeis; por SID, estáveis.
Diagnóstico prático e confiável
Ative o log detalhado do MSI
Refaça a instalação com log verboso. No seu script de inicialização, troque a chamada do msiexec
por:
msiexec /i "\<domínio>\NETLOGON\seu.msi" /qn /L*v "%WinDir%\Temp\seu-msi.log"
Depois abra %WinDir%\Temp\seu-msi.log
e pesquise termos como 1376, NetLocalGroup
, CreateLocalGroup
, LockPermissions
, AddMember
. Nas linhas próximas ao 1376 costuma aparecer o nome exato do grupo que o instalador esperava.
Confirme a existência do grupo no alvo
Use CMD (compatível com Startup Scripts) para listar grupos locais:
net localgroup
net localgroup "Nome do Grupo"
Ou, se puder testar via PowerShell:
Get-LocalGroup | Sort-Object Name | Format-Table Name, SID
Get-LocalGroup -Name "Nome do Grupo" -ErrorAction SilentlyContinue
Caso o grupo não exista, você já confirmou a causa.
Entenda o contexto de execução
O Startup Script roda antes do logon e, por padrão, pode começar antes de a rede estar efetivamente pronta. Isso afeta resolução de nomes, Netlogon, DFS/FRS e até traduções de nome de grupo. Se o instalador tentar checar um grupo embutido “Builtin\…”, a tradução pode falhar temporariamente. Por isso, além de criar o grupo, é essencial garantir a rede no boot (veja adiante).
Solução direta: criar o grupo antes do MSI
Opção com GPO Preferences (recomendada)
- Acesse Computer Configuration → Preferences → Control Panel Settings → Local Users and Groups;
- New → Local Group (Create);
- Informe o nome exato do grupo que o log do MSI mostrou.
Essa abordagem é idempotente (o GPP cria se não existir) e não depende de scripts.
Opção no próprio script, antes do msiexec
rem — Cria o grupo se não existir
net localgroup "Nome exato do grupo" >nul 2>&1
if errorlevel 1 (
net localgroup "Nome exato do grupo" /add
)
Atenção: se o instalador quer um grupo embutido do Windows (por exemplo, um dos grupos Builtin), criar um grupo “de mesmo nome” pode apenas contornar a checagem, mas não entregar os privilégios que o Builtin possui. O ideal é o MSI referenciar SIDs bem conhecidos ou o nome canônico (Builtin\…), não a string localizada. Se você não controla o MSI, a criação do grupo de mesmo nome resolve a instalação; avalie se os privilégios esperados precisam ser configurados por GPO (ver seção seguinte).
Garanta que a rede e o domínio estejam prontos no boot
Ative a política que força o computador a esperar a rede durante inicialização e logon e mantenha scripts de inicialização síncronos:
Item | Caminho | Configuração | Por quê |
---|---|---|---|
Always wait for the network at computer startup and logon | Computer Configuration → Policies → Administrative Templates → System → Logon | Enabled | Garante que DC/Netlogon estejam disponíveis antes do script/MSI. |
Run startup scripts asynchronously | Computer Configuration → Policies → Administrative Templates → System → Scripts | Disabled | Evita sobreposição de etapas e problemas de ordem/tempo. |
Conceda direitos e permissões via GPO (em vez do MSI)
Muitos MSIs falham ao tentar atribuir direitos de logon como serviço ou aplicar ACLs em pastas/registry. Antecipe isso pela própria GPO:
- User Rights Assignment: Computer Configuration → Policies → Windows Settings → Security Settings → Local Policies → User Rights Assignment → adicione a conta de serviço em Log on as a service.
- ACL de pastas/arquivos: use Preferences → Windows Settings → Files/Folders para definir permissões, ou um trecho de script com
icacls
. - Evite conflitos: verifique as políticas SeDenyServiceLogonRight e similares para não negar o logon do serviço por engano.
Exemplo de ajuste de ACL por script
rem — Concede leitura/execução à conta de serviço na pasta do app
icacls "C:\Program Files\MeuApp" /grant "DOMÍNIO\svc-app:(OI)(CI)RX" /T
Remova credenciais do script: use gMSA
Guardar usuário/senha de domínio em texto claro em scripts/GPO é um risco. Sempre que possível, use uma Group Managed Service Account (gMSA). Resumo do fluxo:
- No AD, crie a gMSA e defina quais computadores podem usá-la;
- Instale a gMSA nos servidores-alvo;
- Configure o serviço para iniciar com
DOMÍNIO\conta$
, sem senha.
Exemplo de comandos (executados por um administrador de AD)
# 1) (Uma vez no domínio) criar a chave do KDS, se ainda não existir:
Add-KdsRootKey -EffectiveImmediately
2) Criar a gMSA e permitir que os computadores do grupo "GRP-SERVICOS-APP" a utilizem:
New-ADServiceAccount -Name "gmsaMeuApp" -DNSHostName "meudominio.local" -PrincipalsAllowedToRetrieveManagedPassword "GRP-SERVICOS-APP"
3) Em cada servidor-alvo:
Install-ADServiceAccount -Identity "gmsaMeuApp"
Test-ADServiceAccount -Identity "gmsaMeuApp" # deve retornar True
4) Configurar o serviço para usar a gMSA (sem senha):
sc.exe config "NomeDoServico" obj= "MEUDOMINIO\gmsaMeuApp\$" password= ""
Combine com a GPO de Log on as a service para a gMSA, se necessário. O ganho é imediato: sem senhas em scripts e rotação automática gerenciada pelo AD.
Métodos de implantação mais robustos
Se possível, prefira Software Installation (GPO) em Computer Configuration → Policies → Software Settings → Software installation para atribuir o MSI ao computador. Alternativas: Intune/Endpoint Manager, Configuration Manager, ou outra ferramenta de gerenciamento. Essas soluções reduzem a necessidade de lógica customizada em .cmd
e lidam melhor com ordem de aplicação e retries.
Modelo de script robusto para Startup
Se o Startup Script for o caminho escolhido, eis um esqueleto resiliente que você pode adaptar. Ele verifica/cria o grupo, copia o MSI localmente (evita problemas transitórios de rede), faz log verboso, instala e valida o serviço:
Versão CMD
@echo off
setlocal enabledelayedexpansion
set LOG=%WinDir%\Temp\deploy-meuapp.log
set MSILOG=%WinDir%\Temp\meuapp-msi.log
set MSISRC=\MEUDOMINIO\NETLOGON\MeuApp.msi
set MSILOCAL=%ProgramData%\Deploy\Pacotes\MeuApp.msi
set GRUPO="Performance Log Users" rem <-- troque pelo nome visto no log
set SERVICO=MeuAppSvc
call \:log ===== Início da implantação MeuApp =====
rem Garanta pasta de staging
if not exist "%ProgramData%\Deploy\Pacotes" mkdir "%ProgramData%\Deploy\Pacotes"
rem Copia com tentativas
for /l %%i in (1,1,3) do (
copy /y "%MSISRC%" "%MSILOCAL%" >nul 2>&1
if exist "%MSILOCAL%" goto \:copiado
call \:log Tentativa %%i de copiar MSI falhou, aguardando...
timeout /t 10 /nobreak >nul
)
call \:log ERRO: não foi possível copiar o MSI a partir de %MSISRC%
exit /b 1
\:copiado
call \:log MSI copiado para %MSILOCAL%
rem Cria grupo se necessário
net localgroup %GRUPO% >nul 2>&1 || (
call \:log Grupo %GRUPO% não existe. Criando...
net localgroup %GRUPO% /add
)
rem Instala com log detalhado
call \:log Iniciando msiexec...
msiexec /i "%MSILOCAL%" /qn /L\*v "%MSILOG%"
set RC=%ERRORLEVEL%
call \:log msiexec retornou %RC%
if not "%RC%"=="0" (
call \:log ERRO de instalação. Verifique %MSILOG%
exit /b %RC%
)
rem Valida serviço
sc query "%SERVICO%" | find /i "STATE" >nul 2>&1
if errorlevel 1 (
call \:log Aviso: serviço %SERVICO% não encontrado após a instalação.
) else (
call \:log Serviço %SERVICO% instalado. Iniciando...
sc start "%SERVICO%" >nul 2>&1
)
call \:log ===== Concluído =====
exit /b 0
\:log
echo %date% %time% - %\* >> "%LOG%"
exit /b 0
Versão PowerShell
$ErrorActionPreference = 'Stop'
$Log = "$env:WINDIR\Temp\deploy-meuapp-ps.log"
$MsiLog = "$env:WINDIR\Temp\meuapp-msi.log"
$MsiSrc = "\\MEUDOMINIO\NETLOGON\MeuApp.msi"
$MsiLocal = "$env:ProgramData\Deploy\Pacotes\MeuApp.msi"
$Grupo = "Performance Log Users" # <-- troque com o nome do log
$Servico = "MeuAppSvc"
function Write-Log { param(\[string]\$m) Add-Content -Path \$Log -Value "\$(Get-Date -Format s) \$m" }
Write-Log "==== Início da implantação MeuApp ===="
Staging
\$null = New-Item -ItemType Directory -Path (Split-Path \$MsiLocal) -Force
Cópia com tentativas
\$ok = \$false
1..3 | ForEach-Object {
try {
Copy-Item -Path \$MsiSrc -Destination \$MsiLocal -Force
if (Test-Path \$MsiLocal) { \$ok = \$true; break }
} catch { Write-Log "Tentativa $\ falhou: \$($\.Exception.Message)"; Start-Sleep -Seconds 10 }
}
if (-not \$ok) { Write-Log "ERRO: não foi possível copiar \$MsiSrc"; exit 1 }
Cria grupo se necessário (idempotente)
if (-not (Get-LocalGroup -Name \$Grupo -ErrorAction SilentlyContinue)) {
Write-Log "Grupo '\$Grupo' não existe. Criando..."
New-LocalGroup -Name \$Grupo | Out-Null
}
Instalação MSI com log detalhado
Write-Log "Executando msiexec..."
\$arguments = @("/i `"$MsiLocal`"", "/qn", "/L\*v `"$MsiLog`"")
\$process = Start-Process -FilePath "msiexec.exe" -ArgumentList \$arguments -Wait -PassThru
Write-Log "msiexec retornou \$(\$process.ExitCode)"
if (\$process.ExitCode -ne 0) { Write-Log "Falha na instalação. Veja \$MsiLog"; exit \$process.ExitCode }
Validação do serviço
try {
\$svc = Get-Service -Name \$Servico -ErrorAction Stop
if (\$svc.Status -ne 'Running') { Start-Service -Name \$Servico }
Write-Log "Serviço \$Servico está \$((Get-Service \$Servico).Status)"
} catch {
Write-Log "Aviso: serviço \$Servico não localizado."
}
Write-Log "==== Concluído ===="
Diagnóstico complementar
- Gere um relatório de aplicação de GPO com
gpresult
:gpresult /h C:\gpo.html
Abra oC:\gpo.html
e verifique se a GPO aplicou, se há erros e a ordem de processamento. - No Event Viewer, consulte Applications and Services Logs → Microsoft → Windows → GroupPolicy e Windows Logs → Application (MsiInstaller) para evidências de sequência/tempo e falhas em custom actions.
- Valide a disponibilidade do DC/Netlogon no boot (scripts que fazem um
nltest /dsgetdc:DOMINIO
ou uma simples consulta DNS/LDAP ajudam a confirmar).
Boas práticas para evitar recorrência
- Evite nomes traduzidos: se você controla o pacote, altere-o para referenciar Well-Known SIDs ou o caminho
Builtin\NomeCanônico
do grupo, em vez da string localizada. - Prefira gMSA a usuário/senha em claro. Se não for possível, armazene segredos em um cofre e injete no momento da execução (fora do escopo do artigo, mas é a direção correta).
- Copie o MSI localmente antes de instalar. Instalar diretamente de um share no boot é suscetível a quedas momentâneas.
- Repare a instalação após criar o grupo (se o fornecedor do MSI suportar
REINSTALL=ALL REINSTALLMODE=vomus
), para evitar reinstalações completas.
Sinais que apontam para “grupo inexistente”
Evidência | Indicação | O que fazer |
---|---|---|
Log do MSI com 1376 próximo a LockPermissions /AddMember | MSI tentou mexer em um grupo local que não existe | Crie o grupo antes; ajuste GPP/ACL; reexecute a instalação |
Instalação manual funciona; via GPO falha | Diferença de contexto (rede/LocalSystem) | Habilite “Always wait…”, mantenha scripts síncronos |
Sistema operacional em PT-BR/PT-PT; MSI espera nome em EN-US | Conflito de localização de nomes de grupos embutidos | Prefira SIDs ou crie o grupo com o nome esperado (com cautela) |
Erros relacionados e como distinguir
- 1603 (Fatal error during installation): sintoma genérico; verifique o log para encontrar a causa-raiz (neste caso, 1376).
- 1314 (A required privilege is not held by the client): aparece quando falta um direito como “Log on as a service”. A solução aqui é a seção de User Rights Assignment.
- 1069 (The service did not start due to a logon failure): credenciais da conta de serviço inválidas ou não têm direito de logon como serviço.
Checklist para ação imediata
- Ativar
/L*v
nomsiexec
e identificar o nome do grupo faltante no log; - Pré-criar o grupo por GPO Preferences ou com
net localgroup
antes domsiexec
; - Habilitar Always wait for the network at computer startup and logon e manter scripts síncronos;
- Garantir Log on as a service e ACLs via GPO;
- Remover credenciais do script; preferir gMSA ou configurar o serviço via GPP;
- Validar aplicação de GPO com
gpresult
e logs do Event Viewer.
Perguntas frequentes
Preciso criar exatamente o mesmo nome de grupo que aparece no log?
Se você não controla o MSI, sim — isso geralmente satisfaz a verificação do instalador. Porém, se o nome corresponde a um grupo embutido do Windows, o ideal é corrigir o pacote para mirar o SID daquele grupo ou aplicar as permissões via GPO. Criar um grupo “com o mesmo nome” não o torna equivalente ao embutido.
Como descubro o SID de um grupo local existente?
(Get-LocalGroup -Name "Nome do Grupo").SID.Value
Com isso você consegue validar se o que o instalador precisa é um grupo embutido (SID bem conhecido) ou um grupo novo.
Por que copiar o MSI localmente ajuda?
Durante o boot, a rede/DFS pode oscilar. Ao copiar o MSI para %ProgramData%
e instalar a partir dali, você reduz risco de falha transitória e acelera reexecuções em caso de erro.
Posso usar “Software Installation (GPO)” e ainda assim pré-criar o grupo?
Sim. Inclusive, é uma boa combinação: o GPP garante o grupo/direitos e a política de Software Installation entrega o MSI de forma transacional, com retry e ordem bem definida.
Conclusão
O erro 1376 revela um problema simples, porém traiçoeiro: o instalador referenciou um grupo local inexistente. A correção sólida passa por identificar o nome do grupo no log, criá-lo antes da instalação (via GPP ou script), garantir rede e ordem de processamento (política “Always wait…” e scripts síncronos) e mover ajustes de direitos/ACLs para a GPO. Para endurecer a segurança e simplificar a operação, adote gMSA no serviço em vez de senhas em texto claro. Seguindo esse passo a passo, o MSI deixa de acionar rollback, o serviço inicia corretamente e a sua implantação via GPO passa a ser previsível e repetível.
Resumo de comandos úteis
Objetivo | Comando |
---|---|
Instalar com log detalhado | msiexec /i "Caminho\seu.msi" /qn /L*v "%WinDir%\Temp\seu-msi.log" |
Verificar/criar grupo local | net localgroup "Nome do Grupo" / net localgroup "Nome do Grupo" /add |
Conceder direito de logon como serviço | Via GPO: User Rights Assignment → Log on as a service |
Validar aplicação de GPO | gpresult /h C:\gpo.html |
Definir ACLs por script | icacls "C:\Caminho" /grant "DOM\Conta:(OI)(CI)RX" /T |
Configurar serviço com gMSA | sc.exe config "Servico" obj= "DOM\gmsaConta$" password= "" |
Checklist rápido
- Ativar
/L*v
e identificar o nome do grupo faltante no log; - Pré‑criar o grupo por GPP ou
net localgroup
antes domsiexec
; - Habilitar Always wait for the network… e manter scripts síncronos;
- Garantir Log on as a service e ACLs via GPO;
- Remover credenciais do script; preferir gMSA ou configurar serviço via GPP;
- Validar GPO com
gpresult
.
Resultado esperado: com o grupo local existente (e direitos/ACLs garantidos), o MSI deixa de acionar o erro 1376, o serviço inicia corretamente e a instalação não faz rollback.