diff --git a/EduNetworkBuilder/NB.cs b/EduNetworkBuilder/NB.cs index 111f882..8a2736b 100644 --- a/EduNetworkBuilder/NB.cs +++ b/EduNetworkBuilder/NB.cs @@ -40,7 +40,7 @@ namespace EduNetworkBuilder public enum NBSoundType { none, success, saved_ok, saved_failed } public enum RTFWindowContents { help, about, release_notes } public enum NetTestType { NeedsLocalIPTo, NeedsDefaultGW, NeedsLinkToDevice, NeedsRouteToNet, - SuccessfullyPings, SuccessfullyArps, SuccessfullyDHCPs, HelpRequest, ReadContextHelp, FailedPing, + SuccessfullyPings, SuccessfullyPingsAgain, SuccessfullyArps, SuccessfullyDHCPs, HelpRequest, ReadContextHelp, FailedPing, DHCPServerEnabled, LockAll, LockIP, LockRoute, LockNic, LockDHCP, LockGateway } @@ -304,6 +304,13 @@ namespace EduNetworkBuilder if (myWin.GameRandomGen == null) return null; return myWin.myNetwork; } + public static int nextPacketID() + { + BuilderWindow myWin = (BuilderWindow)Application.OpenForms["BuilderWindow"]; + if (myWin == null) return 1; //return something. + return myWin.nextPacketID(); + } + public static BuilderWindow GetBuilderWin() { BuilderWindow myWin = (BuilderWindow)Application.OpenForms["BuilderWindow"]; diff --git a/EduNetworkBuilder/NetTest.cs b/EduNetworkBuilder/NetTest.cs index 3cedc49..01006e7 100644 --- a/EduNetworkBuilder/NetTest.cs +++ b/EduNetworkBuilder/NetTest.cs @@ -16,6 +16,7 @@ namespace EduNetworkBuilder public Color WrongColor = Color.Red; public NetTestType TheTest = NetTestType.NeedsDefaultGW; public bool TaskWasDone = false; + public int PacketNumber = -1; public NetTest(string srcHost, string dstHost, NetTestType tTest) { @@ -145,6 +146,7 @@ namespace EduNetworkBuilder toreturn = NB.Translate("NT_TstDiscriptDHCPIP"); break; case NetTestType.SuccessfullyPings: + case NetTestType.SuccessfullyPingsAgain: toreturn = NB.Translate("NT_TstDiscriptPing"); break; case NetTestType.HelpRequest: @@ -177,7 +179,6 @@ namespace EduNetworkBuilder case NetTestType.ReadContextHelp: toreturn = NB.Translate("_ReadContext"); break; - } break; case NetTestVerbosity.full: @@ -205,6 +206,7 @@ namespace EduNetworkBuilder toreturn = NB.Translate("NT_TstDiscriptDHCPIP2"); break; case NetTestType.SuccessfullyPings: + case NetTestType.SuccessfullyPingsAgain: toreturn = NB.Translate("NT_TstDiscriptPing2"); break; case NetTestType.HelpRequest: @@ -216,7 +218,6 @@ namespace EduNetworkBuilder case NetTestType.DHCPServerEnabled: toreturn = NB.Translate("NT_TstDiscriptDHCP2"); break; - case NetTestType.LockAll: toreturn = NB.Translate("NT_TstDiscriptLock") + ":"; break; @@ -322,10 +323,14 @@ namespace EduNetworkBuilder return false; //No need to color anything } - public void SetDone() + public void SetDone(int PacketID = -1) { if(TaskWasDone == false) { + if (TheTest == NetTestType.FailedPing || TheTest == NetTestType.SuccessfullyArps + || TheTest == NetTestType.SuccessfullyDHCPs || TheTest == NetTestType.SuccessfullyPings + || TheTest == NetTestType.SuccessfullyPingsAgain) + PacketNumber = PacketID; //Track the packetID of the first packet to complete the task NB.PlaySound(NBSoundType.success); } TaskWasDone = true; @@ -396,6 +401,7 @@ namespace EduNetworkBuilder case NetTestType.SuccessfullyArps: case NetTestType.SuccessfullyDHCPs: case NetTestType.SuccessfullyPings: + case NetTestType.SuccessfullyPingsAgain: case NetTestType.HelpRequest: case NetTestType.ReadContextHelp: case NetTestType.FailedPing: diff --git a/EduNetworkBuilder/Network.cs b/EduNetworkBuilder/Network.cs index 65cbe7f..d9e1542 100644 --- a/EduNetworkBuilder/Network.cs +++ b/EduNetworkBuilder/Network.cs @@ -471,7 +471,8 @@ namespace EduNetworkBuilder { if (nt.sHost == Source && !nt.TestComplete()) { - if (forPing && (nt.TheTest == NetTestType.FailedPing || nt.TheTest == NetTestType.SuccessfullyPings)) + if (forPing && (nt.TheTest == NetTestType.FailedPing || nt.TheTest == NetTestType.SuccessfullyPings + || nt.TheTest == NetTestType.SuccessfullyPingsAgain)) tDests.Add(nt.dHost); if (!forPing && nt.TheTest == NetTestType.SuccessfullyArps) tDests.Add(nt.dHost); @@ -688,23 +689,47 @@ namespace EduNetworkBuilder /// The type of packet that arrived /// The host it originated from /// The machine it went to - public void NotePacketArrived(PacketType packet_type, NetworkDevice source, IPAddress sIP, IPAddress dIP) + public void NotePacketArrived(PacketType packet_type, NetworkDevice source, IPAddress sIP, IPAddress dIP, int PacketID) { string sHost = ReverseDNSLookup(source, sIP); string dHost = ReverseDNSLookup(source, dIP); + //If we are checking a ping, but we already have done it, we see if there is a ping-again foreach (NetTest nt in NetTests) { if (nt.TheTest == NetTestType.SuccessfullyArps && packet_type == PacketType.arp_answer && sHost == nt.sHost && dHost == nt.dHost) nt.SetDone(); if (nt.TheTest == NetTestType.SuccessfullyDHCPs && packet_type == PacketType.dhcp_answer && sHost == nt.sHost && dHost == nt.dHost) nt.SetDone(); + if(HasCompletedPingTest(packet_type,source,sIP,dIP, PacketID)) + { + if (nt.TheTest == NetTestType.SuccessfullyPingsAgain && packet_type == PacketType.ping_answer && sHost == nt.sHost && dHost == nt.dHost) + nt.SetDone(PacketID); + if (nt.TheTest == NetTestType.SuccessfullyPingsAgain && packet_type == PacketType.ping_answer && sHost == nt.sHost && dHost == null && dIP != null && dIP.BroadcastAddress == dIP.GetIP && dIP.GetIPString == nt.dHost) + nt.SetDone(PacketID); + } if (nt.TheTest == NetTestType.SuccessfullyPings && packet_type == PacketType.ping_answer && sHost == nt.sHost && dHost == nt.dHost) - nt.SetDone(); + nt.SetDone(PacketID); if (nt.TheTest == NetTestType.SuccessfullyPings && packet_type == PacketType.ping_answer && sHost == nt.sHost && dHost == null && dIP != null && dIP.BroadcastAddress == dIP.GetIP && dIP.GetIPString == nt.dHost) - nt.SetDone(); + nt.SetDone(PacketID); } } + public bool HasCompletedPingTest(PacketType packet_type, NetworkDevice source, IPAddress sIP, IPAddress dIP, int PacketID) + { + if (packet_type != PacketType.ping_answer) return false; //This only works with pings. + string sHost = ReverseDNSLookup(source, sIP); + string dHost = ReverseDNSLookup(source, dIP); + //If this matches a ping test which is already set to "done", return true + foreach (NetTest nt in NetTests) + { + if (nt.TheTest == NetTestType.SuccessfullyPings && sHost == nt.sHost && dHost == nt.dHost && nt.TaskWasDone && nt.PacketNumber != PacketID) + return true; + if (nt.TheTest == NetTestType.SuccessfullyPings && sHost == nt.sHost && dHost == null && dIP != null && dIP.BroadcastAddress == dIP.GetIP && dIP.GetIPString == nt.dHost && nt.TaskWasDone && nt.PacketNumber != PacketID) + return true; + } + return false; + } + public bool NoteActionDone(NetTestType theTest, string sHost, string dHost) { bool OldVal = false; diff --git a/EduNetworkBuilder/NetworkBuilder.cs b/EduNetworkBuilder/NetworkBuilder.cs index b88f01c..807d77f 100644 --- a/EduNetworkBuilder/NetworkBuilder.cs +++ b/EduNetworkBuilder/NetworkBuilder.cs @@ -19,6 +19,7 @@ namespace EduNetworkBuilder public partial class BuilderWindow : Form { public Random GameRandomGen = new Random(); + private int LastPacketID=1; public DebugPausePoint DebugSetting = DebugPausePoint.none; // public DebugPausePoint DebugSetting = DebugPausePoint.all | DebugPausePoint.dump; public Network myNetwork = new Network(""); @@ -479,6 +480,11 @@ namespace EduNetworkBuilder return false; } + public int nextPacketID() + { + return LastPacketID++; + } + public List GetPuzzleTags() { List PuzzleTags = new List(); @@ -562,15 +568,25 @@ namespace EduNetworkBuilder pbNetworkView.ContextMenuStrip.Items.Clear(); if (ReleasedOn != null && ReleasedOn.IsNotNetDevice()) { + List DoneList = new List(); foreach (string tStr in myNetwork.GetIncompleteTestDestinations(ReleasedOn.hostname, true)) { - pbNetworkView.ContextMenuStrip.Items.Add(string.Format(NB.Translate("_PingStr"),tStr)); - pbNetworkView.ContextMenuStrip.Items[index++].Click += pbNetworkView_Ping_Name_Click; + if (!DoneList.Contains(tStr)) + { + pbNetworkView.ContextMenuStrip.Items.Add(string.Format(NB.Translate("_PingStr"), tStr)); + pbNetworkView.ContextMenuStrip.Items[index++].Click += pbNetworkView_Ping_Name_Click; + DoneList.Add(tStr); + } } + DoneList.Clear(); foreach (string tStr in myNetwork.GetIncompleteTestDestinations(ReleasedOn.hostname, false)) { - pbNetworkView.ContextMenuStrip.Items.Add(string.Format(NB.Translate("H_ARP_TitleStr"), tStr)); - pbNetworkView.ContextMenuStrip.Items[index++].Click += pbNetworkView_Arp_Name_Click; + if (!DoneList.Contains(tStr)) + { + pbNetworkView.ContextMenuStrip.Items.Add(string.Format(NB.Translate("H_ARP_TitleStr"), tStr)); + pbNetworkView.ContextMenuStrip.Items[index++].Click += pbNetworkView_Arp_Name_Click; + DoneList.Add(tStr); + } } } if (ReleasedOn != null && ReleasedOn.IsNotNetDevice()) diff --git a/EduNetworkBuilder/NetworkDevice.cs b/EduNetworkBuilder/NetworkDevice.cs index ba77e7c..9cebb8c 100644 --- a/EduNetworkBuilder/NetworkDevice.cs +++ b/EduNetworkBuilder/NetworkDevice.cs @@ -1533,7 +1533,7 @@ namespace EduNetworkBuilder bool isbroadcast = HasBroadcastAddress(tPacket); if (!isbroadcast || (isbroadcast && HasLocalNic(tPacket.sourceIP))) { - nPacket = new Packet(this, tPacket.sourceIP, "", PacketType.ping_answer); + nPacket = new Packet(this, tPacket.sourceIP, "", PacketType.ping_answer, tPacket.packetID); nPacket.OriginalDestIP = tPacket.destIP; nPacket.isFresh = true; //So it starts from here nPacket.Tracking = new PacketMessage(); @@ -1605,11 +1605,11 @@ namespace EduNetworkBuilder tPacket.MyStatus = PacketStatus.finished_ok; if (tPacket.sourceIP.GetIP != 0) { - myNet.NotePacketArrived(tPacket.MyType, this, tPacket.destIP, tPacket.OriginalDestIP); + myNet.NotePacketArrived(tPacket.MyType, this, tPacket.destIP, tPacket.OriginalDestIP, tPacket.packetID); } else { - myNet.NotePacketArrived(tPacket.MyType, this, tPacket.destIP, tPacket.sourceIP); + myNet.NotePacketArrived(tPacket.MyType, this, tPacket.destIP, tPacket.sourceIP, tPacket.packetID); } } } @@ -1688,7 +1688,7 @@ namespace EduNetworkBuilder StoreArp(tPacket.sourceMAC, tPacket.TsourceIP.GetIP.ToIpString(), myid); tPacket.Tracking.Status = NB.LeftPad(hostname) + " " + string.Format(NB.Translate("ND_ProssArrArpSuccessStr"), tPacket.sourceIP.GetIP.ToIpString(), tPacket.sourceIP.GetIP.ToIpString(), tPacket.sourceMAC); tPacket.MyStatus = PacketStatus.finished_ok; //Yay! - myNet.NotePacketArrived(tPacket.MyType, this, tPacket.destIP, tPacket.sourceIP); + myNet.NotePacketArrived(tPacket.MyType, this, tPacket.destIP, tPacket.sourceIP, tPacket.packetID); } else { @@ -1764,7 +1764,7 @@ namespace EduNetworkBuilder IsDirty = true; //If we need to redraw the device IP tPacket.Tracking.Status = NB.LeftPad(hostname) + " " + string.Format(NB.Translate("ND_ProssArrDHCPAnsStr"), tPacket.payloadIP.GetIP.ToIpString()); tPacket.MyStatus = PacketStatus.finished_ok; //Yay! - myNet.NotePacketArrived(tPacket.MyType, this, tPacket.payloadIP, tPacket.sourceIP); + myNet.NotePacketArrived(tPacket.MyType, this, tPacket.payloadIP, tPacket.sourceIP, tPacket.packetID); return; } } diff --git a/EduNetworkBuilder/Packet.cs b/EduNetworkBuilder/Packet.cs index e523746..5f7529f 100644 --- a/EduNetworkBuilder/Packet.cs +++ b/EduNetworkBuilder/Packet.cs @@ -35,6 +35,7 @@ namespace EduNetworkBuilder Tracking.Finished = true; } } + public int packetID; public int TTL = 20; public int TickTTL = 50; public int health = 100; @@ -106,12 +107,21 @@ namespace EduNetworkBuilder health = copyfrom.health; StartTime = copyfrom.StartTime; OriginalDestIP = copyfrom.OriginalDestIP; + packetID = copyfrom.packetID; Tracking.AddMessage(DebugLevel.debug, WhereAmI, NB.Translate("P_PacketDuplicated")); } //Generate a packet with the given payload. - public Packet(NetworkComponent start, string source, string dest, string payload, PacketType theType) + public Packet(NetworkComponent start, string source, string dest, string payload, PacketType theType, int NewPacketID=-1) { + if (NewPacketID == -1) + { + packetID = NB.nextPacketID(); + } + else + { + packetID = NewPacketID; + } WhereAmI = start; payloadData = payload; MyType = theType; @@ -141,12 +151,20 @@ namespace EduNetworkBuilder isFresh = true; } - public Packet(NetworkComponent start, IPAddress dest, string payload, PacketType theType) + public Packet(NetworkComponent start, IPAddress dest, string payload, PacketType theType, int NewPacketID = -1) { WhereAmI = start; payloadData = payload; MyType = theType; - + if (NewPacketID == -1) + { + packetID = NB.nextPacketID(); + } + else + { + packetID = NewPacketID; + } + if (theType != PacketType.arp_answer && theType != PacketType.arp_request) { sourceIP = new IPAddress(NB.ZeroIPString); diff --git a/EduNetworkBuilder/Resources/Level0_NetworkLoop.enbx b/EduNetworkBuilder/Resources/Level0_NetworkLoop.enbx index c1841ec..eb7b293 100644 --- a/EduNetworkBuilder/Resources/Level0_NetworkLoop.enbx +++ b/EduNetworkBuilder/Resources/Level0_NetworkLoop.enbx @@ -9,7 +9,7 @@ 100 False 0 - 3 + 3.4 171 full diff --git a/EduNetworkBuilder/Resources/Level0_NetworkLoop2.enbx b/EduNetworkBuilder/Resources/Level0_NetworkLoop2.enbx index 2d50dd5..beb70cb 100644 --- a/EduNetworkBuilder/Resources/Level0_NetworkLoop2.enbx +++ b/EduNetworkBuilder/Resources/Level0_NetworkLoop2.enbx @@ -1630,6 +1630,11 @@ pc0 pc1 SuccessfullyPings + + + pc0 + pc1 + SuccessfullyPingsAgain Ping diff --git a/EduNetworkBuilder/Resources/ReleaseNotes.rtf b/EduNetworkBuilder/Resources/ReleaseNotes.rtf index 291597f..03422a1 100644 --- a/EduNetworkBuilder/Resources/ReleaseNotes.rtf +++ b/EduNetworkBuilder/Resources/ReleaseNotes.rtf @@ -6,7 +6,9 @@ * Hide gateway label when we do not need it. (ip-address editor)\par * rename "mixed network" puzzle to be "adding devices" (the puzzle was about adding devices)\par * Changed layout of many messages\par -* Save the level we are working on. Allows us to finish level 5 before level 3 if we want to.\b\par +* Save the level we are working on. Allows us to finish level 5 before level 3 if we want to.\par +* Make network-loop puzzles sit next to each-other\par +* Make it so network-loop2 puzzle asks for second ping after first one finishes \b\par Version 1.0.24 \par \b0 * Add sound when ctrl-s is pressed so we know we saved.\par * Add sound fail when save is canceled (will use it later if ctrl-s fails)\par