diff --git a/wpa_supplicant/ctrl_iface.c b/wpa_supplicant/ctrl_iface.c
index 0fb84e435..126dfabea 100644
--- a/wpa_supplicant/ctrl_iface.c
+++ b/wpa_supplicant/ctrl_iface.c
@@ -10116,6 +10116,15 @@ static int wpas_ctrl_iface_send_twt_setup(struct wpa_supplicant *wpa_s,
 	int exponent = 10;
 	int mantissa = 8192;
 	int min_twt = 255;
+	unsigned long long twt = 0;
+	int requestor = 1;
+	int setup_cmd = 0;
+	int trigger = 1;
+	int implicit = 1;
+	int flow_type = 1;
+	int flow_id = 0;
+	int protection = 0;
+	int twt_channel = 0;
 
 	char* tok_s = os_strstr(cmd, "dialog=");
 	if (tok_s)
@@ -10129,7 +10138,45 @@ static int wpas_ctrl_iface_send_twt_setup(struct wpa_supplicant *wpa_s,
 	if (tok_s)
 		exponent = atoi(tok_s + strlen("mantissa="));
 
-	ret = wpas_twt_send_setup(wpa_s, dtok, exponent, mantissa, min_twt);
+	tok_s = os_strstr(cmd, "setup_cmd=");
+	if (tok_s)
+		setup_cmd = atoi(tok_s + strlen("setup_cmd="));
+
+	tok_s = os_strstr(cmd, "twt=");
+	if (tok_s)
+		sscanf(tok_s + strlen("twt="), "%llu", &twt);
+
+	tok_s = os_strstr(cmd, "requestor=");
+	if (tok_s)
+		requestor = atoi(tok_s + strlen("requestor="));
+
+	tok_s = os_strstr(cmd, "trigger=");
+	if (tok_s)
+		trigger = atoi(tok_s + strlen("trigger="));
+
+	tok_s = os_strstr(cmd, "implicit=");
+	if (tok_s)
+		implicit = atoi(tok_s + strlen("implicit="));
+
+	tok_s = os_strstr(cmd, "flow_type=");
+	if (tok_s)
+		flow_type = atoi(tok_s + strlen("flow_type="));
+
+	tok_s = os_strstr(cmd, "flow_id=");
+	if (tok_s)
+		flow_id = atoi(tok_s + strlen("flow_id="));
+
+	tok_s = os_strstr(cmd, "protection=");
+	if (tok_s)
+		protection = atoi(tok_s + strlen("protection="));
+
+	tok_s = os_strstr(cmd, "twt_channel=");
+	if (tok_s)
+		twt_channel = atoi(tok_s + strlen("twt_channel="));
+
+	ret = wpas_twt_send_setup(wpa_s, dtok, exponent, mantissa, min_twt, setup_cmd,
+				  twt, requestor, trigger, implicit, flow_type, flow_id,
+				  protection, twt_channel);
 
 	return ret;
 }
diff --git a/wpa_supplicant/twt.c b/wpa_supplicant/twt.c
index 39fb5a629..da54260fd 100644
--- a/wpa_supplicant/twt.c
+++ b/wpa_supplicant/twt.c
@@ -25,15 +25,18 @@
  * @exponent: TWT wake-interval exponent
  * @mantissa:  TWT wake-interval Mantissa
  * @min_twt:  TWT Minimum TWT Wake Duration.
+ * @setup_cmd: 0 == request, 1 == suggest, etc.  table 9-297
  * Returns: 0 in case of success, negative error code otherwise
  *
  */
 int wpas_twt_send_setup(struct wpa_supplicant *wpa_s,
-			int dtok, int exponent, int mantissa, int min_twt)
+			int dtok, int exponent, int mantissa, int min_twt, int setup_cmd,
+			u64 twt, int requestor, int trigger, int implicit, int flow_type, int flow_id,
+			int protection, int twt_channel)
 {
 	struct wpabuf *buf;
 	u16 req_type = 0;
-	unsigned char targ_wait_time[8] = {0};
+	int i;
 
 	if (wpa_s->wpa_state != WPA_COMPLETED || wpa_s->current_ssid == NULL) {
 		wpa_dbg(wpa_s, MSG_DEBUG, "TWT: No connection, no TWT.");
@@ -43,7 +46,7 @@ int wpas_twt_send_setup(struct wpa_supplicant *wpa_s,
 	/* 3 = action category + action code + dialog token */
 	/* 17 = target wait time IE */
 	buf = wpabuf_alloc(3 + 17);
-	
+
 	if (buf == NULL) {
 		wpa_dbg(wpa_s, MSG_DEBUG,
 			"TWT: Failed to allocate TWT Setup Request");
@@ -63,18 +66,25 @@ int wpas_twt_send_setup(struct wpa_supplicant *wpa_s,
 
 	wpabuf_put_u8(buf, 0x10); /* control field */
 
-	req_type |= (0x1); /* This STA is a TWT Requesting STA */
-	req_type |= (0x70); /* TWT SP includes trigger frames, TWT Implicit, TWT un-announced */
+	req_type |= (requestor & 0x1); /* This STA is a TWT Requesting STA */
+	req_type |= (setup_cmd & 0x7) << 1;
+	req_type |= (trigger & 0x1) << 4;
+	req_type |= (implicit & 0x1) << 5;
+	req_type |= (flow_type & 0x1) << 6;
+	req_type |= (flow_id & 0x7) << 7;
 	req_type |= ((exponent & 0x1f) << 10);
-	/* high bit is 'protection, leave it false for now */
+	req_type |= (protection & 0x1) << 15;
+
 	wpabuf_put_u8(buf, req_type);
 	wpabuf_put_u8(buf, req_type >> 8);
-	/* Not sure exactly how this is used */
-	wpabuf_put_data(buf, targ_wait_time, sizeof(targ_wait_time));
+
+	for (i = 0; i<8; i++) {
+		wpabuf_put_u8(buf, twt >> i);
+	}
 	wpabuf_put_u8(buf, min_twt); /* minimum twt wake duration */
 	wpabuf_put_u8(buf, mantissa);
 	wpabuf_put_u8(buf, mantissa >> 8);
-	wpabuf_put_u8(buf, 0); /* twt channel */
+	wpabuf_put_u8(buf, twt_channel); /* twt channel */
 
 	if (wpa_drv_send_action(wpa_s, wpa_s->assoc_freq, 0, wpa_s->bssid,
 				wpa_s->own_addr, wpa_s->bssid,
diff --git a/wpa_supplicant/wpa_cli.c b/wpa_supplicant/wpa_cli.c
index ba57d7d91..942f64a9d 100644
--- a/wpa_supplicant/wpa_cli.c
+++ b/wpa_supplicant/wpa_cli.c
@@ -3835,7 +3835,7 @@ static const struct wpa_cli_cmd wpa_cli_commands[] = {
 	},
 	{ "twt_setup",
 	  wpa_cli_cmd_twt_setup, NULL, cli_cmd_flag_none,
-	  "[dialog=<token>] [exponent=<exponent>] [mantissa=<mantissa>]"
+	  "[dialog=<token>] [exponent=<exponent>] [mantissa=<mantissa>] [setup_cmd=<setup-cmd>] [twt=<u64>] [requestor=0|1] [trigger=0|1] [implicit=0|1] [flow_type=0|1] [flow_id=<3-bit-id>] [protection=0|1] [twt_channel=<twt chanel id>]"
 	},
 	{ "twt_teardown",
 	  wpa_cli_cmd_twt_teardown, NULL, cli_cmd_flag_none,
diff --git a/wpa_supplicant/wpa_supplicant_i.h b/wpa_supplicant/wpa_supplicant_i.h
index 0271c5e24..ce2586ac9 100644
--- a/wpa_supplicant/wpa_supplicant_i.h
+++ b/wpa_supplicant/wpa_supplicant_i.h
@@ -1559,7 +1559,9 @@ int wpas_get_op_chan_phy(int freq, const u8 *ies, size_t ies_len,
 			 u8 *op_class, u8 *chan, u8 *phy_type);
 
 int wpas_twt_send_setup(struct wpa_supplicant *wpa_s,
-			int dtok, int exponent, int mantissa, int min_twt);
+			int dtok, int exponent, int mantissa, int min_twt, int setup_cmd,
+			u64 twt, int requestor, int trigger, int implicit, int flow_type, int flow_id,
+			int protection, int channel);
 int wpas_twt_send_teardown(struct wpa_supplicant *wpa_s,
 			   int flags);
 
