projectdiscovery/nuclei · error
waiting for password prompt: %w
Error message
waiting for password prompt: %w
What it means
Telnet authentication flow failed while waiting for the server's password prompt. telnetmini.Client.Auth reads from the connection until one of the configured PasswordPrompts appears; readUntil honors the caller-supplied context, so the wrapped error is usually a context deadline/timeout or a connection read error. The username was sent successfully, so the failure is strictly about the password prompt never matching within the ctx budget.
Source
Thrown at pkg/utils/telnetmini/telnet.go:219
return supportsEncryption, options
}
// Auth performs a minimal Telnet username/password interaction.
// It waits for a username/login prompt, sends username, waits for a password prompt,
// sends password, and then looks for fail banners or shell prompts.
// A timeout should be enforced via ctx.
func (c *Client) Auth(ctx context.Context, username, password string) error {
// Wait for username/login prompt
if _, _, err := c.readUntil(ctx, c.UserPrompts...); err != nil {
return fmt.Errorf("waiting for login/username prompt: %w", err)
}
if err := c.writeLine(ctx, username); err != nil {
return fmt.Errorf("sending username: %w", err)
}
// Wait for password prompt
if _, _, err := c.readUntil(ctx, c.PasswordPrompts...); err != nil {
return fmt.Errorf("waiting for password prompt: %w", err)
}
if err := c.writeLine(ctx, password); err != nil {
return fmt.Errorf("sending password: %w", err)
}
// Post-auth: look quickly for explicit failure, else accept shell prompt / silence.
match, got, err := c.readUntil(ctx,
append(append([]string{}, c.FailBanners...), c.ShellPrompts...)...,
)
if err != nil && !errors.Is(err, context.DeadlineExceeded) {
return fmt.Errorf("post-auth read: %s (got: %s)", preview(got, 200), err)
}
low := strings.ToLower(match)
for _, fb := range c.FailBanners {
if low == strings.ToLower(fb) {
return errors.New("authentication failed")
}
}View on GitHub (pinned to 265b3a3dec)
Solutions
- Increase the ctx deadline passed to Auth (the comment says a timeout must be enforced via ctx; make it long enough for a slow login banner exchange).
- Inspect the raw session bytes (readUntil returns what it got) and add the exact password prompt string to Client.PasswordPrompts (defaults expect classic 'Password:' style prompts).
- Verify the service actually requires username/password telnet auth and that UserPrompts matched the real login prompt — an early/incorrect username write can suppress the password prompt.
- Check network health: a reset connection surfaces the same call site as a read error.
Example fix
// before ctx, cancel := context.WithTimeout(ctx, 2*time.Second) err := client.Auth(ctx, "admin", "pass") // after ctx, cancel := context.WithTimeout(ctx, 15*time.Second) err := client.Auth(ctx, "admin", "pass") // and, if the prompt is non-standard: // client.PasswordPrompts = append(client.PasswordPrompts, "Passcode:")
Defensive patterns
Strategy: validation
Validate before calling
ctx, cancel := context.WithTimeout(context.Background(), 15*time.Second)
defer cancel()
// optional: probe the service first
if conn, err := net.DialTimeout("tcp", addr, 5*time.Second); err != nil {
return fmt.Errorf("target unreachable: %w", err)
}
_ = conn.Close()
err := client.Auth(ctx, user, pass) Type guard
func isTelnetAuthPromptErr(err error) bool {
return err != nil && strings.HasPrefix(err.Error(), "waiting for password prompt:")
} Try / catch
if err := client.Auth(ctx, user, pass); err != nil {
if isTelnetAuthPromptErr(err) { /* prompt mismatch or timeout: adjust prompts/ctx, do not retry blindly */ }
return err
} Prevention
- Configure PasswordPrompts to match the exact prompt bytes the target emits (capture a raw session once).
- Give ctx a deadline larger than the slowest observed banner-to-prompt delay.
- Skip Auth for services that use nonstandard handshakes; drive reads manually with readUntil.
When it happens
Trigger: Calling Client.Auth(ctx, user, pass) where ctx has a short/zero deadline, the service's password prompt text does not match any entry in Client.PasswordPrompts, the server rejected the username silently (no prompt follows), or the TCP connection was closed between the username write and this read.
Common situations: Custom telnet-like services with non-standard prompts (e.g. 'Passcode:', localized prompts), a UserPrompts regex/string matching the wrong line so the username is sent too early, firewall/middlebox dropping the connection after login banner, or an aggressive ctx timeout in a scanner harness.
Related errors
- authentication failed
- failed to read response: %w
- failed to send encryption packet: %w
- sending password: %w
- post-auth read: %s (got: %s)
AI-assisted analysis of projectdiscovery/nuclei@265b3a3dec (2026-08-15).
Data as JSON: /api/errors/e5c21937f15a7bec.
Report an issue: GitHub.