How to set variable in second process from first process - vb.net

first of all: I'm a newbie in this forum and not a professional programmer, just hobby.
This is what I have: One solution in VisualStudio with 3 Projects in VB.net.
First project contains common functions etc.
Second project is a windows service.
Third project is a Windows Forms UI.
Second an third project imports the first project.
My problem: When the service from second project is running and UI from third project is started I want to set a variable (e.g. by pressing a button) that will be set in the service, too. So the service is informed to do some special things.
I've tried to declare this variable in the common project, but this doesn't work. After searching a bit I know now this can't work, because the service and the UI are seperate processes.
There are several solutions to communicate between processes, e.g. IPC, shared memory, named pipes....
But isn't there a simple way to solve my problem ?
Thanks a lot and with best regards,
Matthias

OK, thanks for your answers!! :-)
I decided to try it with memory mapped file.
This is my making function:
Public Function MakeMemoryMappedFile(ByVal pValue As String) As String
Dim Buffer As Byte() = ASCIIEncoding.ASCII.GetBytes(pValue)
Try
Dim mmf As MemoryMappedFile = MemoryMappedFile.CreateOrOpen("test", 10000)
Dim accessor As MemoryMappedViewAccessor = mmf.CreateViewAccessor()
accessor.Write(54, CType(Buffer.Length, UShort))
accessor.WriteArray(54 + 2, Buffer, 0, Buffer.Length)
Return "ok"
Catch ex As Exception
Return "Error = " & ex.Message
End Try
End Function
And this is my reading function:
Public Function ReadMemoryMappedFile() As String
Try
Dim mmf As MemoryMappedFile = MemoryMappedFile.OpenExisting("test")
Dim accessor As MemoryMappedViewAccessor = mmf.CreateViewAccessor()
Dim Size As UShort = accessor.ReadUInt16(54)
Dim Buffer As Byte() = New Byte(Size - 1) {}
accessor.ReadArray(54 + 2, Buffer, 0, Buffer.Length)
Return ASCIIEncoding.ASCII.GetString(Buffer)
Catch noFile As FileNotFoundException
Return "No File found ..."
Catch ex As Exception
Return "Error = " & ex.Message
End Try
End Function
I have on my application a button for setting the value and one button for reading the value -> works fine.
If I start this application twice and set the value in the first instance and then read the value from the second instance -> it works fine.
But: If I set the value in the application my windows service can't read ist. Always got a "FileNotFoundException".
Could you please tell me whats wrong ?!?
Thanks !!!

Related

Why a specific folder isn't accessible even if my program is executed as admin?

Hi people!
So right now I'm making a Minecraft Launcher, but I have a problem. I need to list every libraries in the .minecraft libraries folder, but the launcher can't access it even if it's executed as administrator.
Here is the code that fails :
Try
FileList = File.ReadAllLines(AppDataDir & "\libraries").ToList()
Catch ex As Exception
MsgBox(ex.Message)
End Try
The FileList variable :
Dim FileList As New List(Of String)
I need to make it a list of string because of this code :
Dim GameLibs As String = Nothing
For i = 0 To FileList.Count - 1
GameLibs += FileList.Item(i) + ";" + Environment.NewLine()
Next
So now I'm stuck with this problem, but I can't understand it since it works nicely with any other folder.
Oh and, the AppDataDir variable is just the .minecraft directory.
Any help would be great! Thanks if you tried to help me anyway.
I think you just missed the file name and its extension, try to add that line like this one:
FileList = File.ReadAllLines(AppDataDir & "\libraries.txt").ToList()
I hope that helps.
^_^

Reading meta-data locks file

I have the following function to read the recording date of a .jpg-file:
Public Shared Function GetRecordingDateOfPhoto(pathOfPhoto As String) As DateTime
If Not IO.File.Exists(pathOfPhoto) Then
Throw New FileNotFoundException
End If
Dim bitmapSource As BitmapSource = BitmapFrame.Create(New Uri(pathOfPhoto, UriKind.Relative))
Dim bitmapMetadata As BitmapMetadata = TryCast(bitmapSource.Metadata, BitmapMetadata)
Dim result As DateTime
If DateTime.TryParse(bitmapMetadata.DateTaken, result) Then
Return result
Else
Throw New FormatException
End If
End Function
This function returns the correct date, but when I do something like this
dim dateOfPhoto as Date = GetRecordingDateOfPhoto("foo.jpg")
My.Computer.FileSystem.MoveFile("foo.jpg", "bar.jpg")
then I get an exception from MoveFile(...): IOException ("The Process Cannot Access the File Because It Is Being Used by Another Process")
What do I have to change exactly (maybe using/end using?) in the GetRecordingDateOfPhoto(...)-function to avoid this exception?
Many thanks in advance.
Unfortunately, this class is just terribly implemented. Blame Microsoft. BitmapFrame.Create internally creates a stream and never closes it.
source: microsoft .net reference source
This is happening because the function is Shared. Its local variables exist only once regardless of how many class instantiations there are. Try making it not shared or set your variables to Nothing.

Serialization between two applications

I have developed a Visual Basic.net application that uses serialization to save an object. I am wanting to open and save this object in two different Visual Basic.net applications.
What is the best way to do this? Do I need to create a class library to do this?
Can I please have some help for this?
EDIT
I am wanting to be able to open and save the object in both applications.
Depending on how complicated your data is, you should be able to simply mark your data's class with a <Serializable> attribute. You can then simply call the Serialize method in one application, save to disk, then read the file into your other application and call Deserialize.
You will need to define the class in both applications, which is easiest to do by sharing a common library.
See the MDSN example for basic serialization.
You can write/read to xml, then you would just have to check the folder where you save them from the other app to see if a new file has been created or updated.
Function to serialize object and write to xml
Public Function MyObjectFileGeneration()
Try
Dim strPath As String = System.IO.Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().CodeBase)
strPath = Replace(strPath, "file:\", "")
Dim myObj = Form1.MyObject
Dim objStreamWriter As New StreamWriter(strPath & "\MyFolder\MyObj.xml", False)
Dim x As New XmlSerializer(s.GetType)
x.Serialize(objStreamWriter, MyObj)
objStreamWriter.Close()
Return True
Catch ex As Exception
'Do something here if failure...
Return False
End Try
End Function
Function to read xml and de-serialize to object
Public Function GetMyObjFromXMLFile() As MyObj
'check if file exists first...
If xmlFileExists() Then
Dim strPath As String = System.IO.Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().CodeBase)
Dim objStreamReader As New StreamReader(Replace(strPath & "\MyFolder\MyObj.xml", "file:\", ""))
Dim MyObj As New MyObject
Dim x As New XmlSerializer(MyObj.GetType)
MyObj = x.Deserialize(objStreamReader)
objStreamReader.Close()
Return MyObj
Else
Return New MyObj
End If
End Function
I wish there was an easy way to do this, but unfortunately, I hit this wall also..
Serializable data can only be reread by the SAME application. (it gives you a lovely error message about this.) I tried using a serialized connection for simplified packet transfers, unsuccessfully..
Depending on how good you are at programming, I have a recommendation on this one..
Serialize your variables to a memorystream, then cut the header section out and shove it to another file stream, then when you reload it, save a variable to a memorystream to get the new header, then attach the remaining data, then read serialization..
haven't tried it yet, but when I get back to it, this is my next method.
I did see an XML method, but recommend using a compression/encryption library to keep your data safe.. did see some simple ways to possibly do that..
Sorry, I don't have code on this round, but when I investigate it, I will append this response..

VB.NET Checking if a File is Open before proceeding with a Read/Write?

Is there a method to verify that a file is open? The only thing I can think of is the Try/Catch to see if i can catch the file-open exception but I figured that a method be available to return true/false if file is open.
Currently using System.IO and the following code under class named Wallet.
Private holdPath As String = "defaultLog.txt"
Private _file As New FileStream(holdPath, FileMode.OpenOrCreate, FileAccess.ReadWrite)
Private file As New StreamWriter(_file)
Public Function Check(ByVal CheckNumber As Integer, ByVal CheckAmount As Decimal) As Decimal
Try
file.WriteLine("testing")
file.Close()
Catch e As IOException
'Note sure if this is the proper way.
End Try
Return 0D
End Function
Any pointers will be appreciated! Thank you!!
Private Sub IsFileOpen(ByVal file As FileInfo)
Dim stream As FileStream = Nothing
Try
stream = file.Open(FileMode.Open, FileAccess.ReadWrite, FileShare.None)
stream.Close()
Catch ex As Exception
If TypeOf ex Is IOException AndAlso IsFileLocked(ex) Then
' do something here, either close the file if you have a handle, show a msgbox, retry or as a last resort terminate the process - which could cause corruption and lose data
End If
End Try
End Sub
Private Shared Function IsFileLocked(exception As Exception) As Boolean
Dim errorCode As Integer = Marshal.GetHRForException(exception) And ((1 << 16) - 1)
Return errorCode = 32 OrElse errorCode = 33
End Function
Call it like this:
Call IsFileOpen(new FileInfo(filePath))
There is really no point using a 'is file in use check' function since you will still need to have try catch to handle the case that the file fails to open. The file open can fail for many more reasons than it just being already open.
Also using a function to do a check is no guarantee of success. The 'is file in use check' might return false only for the file open to fail with a file already open error, because in time between the check and trying to open the file it was opened by someone else.
It looks like the two suggestions from this MSDN forum posting both involve trying to open the file.
The first one is similar to what you are doing now, and the second involves using a Windows API function (CreateFile) and checking for a invalid handle signifying the file is in use. In both cases they are relying on an error condition to determine if the file is open or not. In short, in my opinion the method you are using is correct since there is not a System.IO.File.IsOpen property.

VB.net Parsing HTML 100 times. Will it work?

Imports System.Web
Imports System.Net
Imports System.Net.ServicePointManager
Public Class GetSource
Function GetHtml(ByVal strPage As String) As String
tryAgain:
ServicePointManager.UseNagleAlgorithm = True
ServicePointManager.Expect100Continue = True
ServicePointManager.CheckCertificateRevocationList = True
ServicePointManager.DefaultConnectionLimit = 100
Dim strReply As String = "NULL"
Try
Dim objhttprequest As System.Net.HttpWebRequest
Dim objhttpresponse As System.Net.HttpWebResponse
objhttprequest = System.Net.HttpWebRequest.Create(strPage)
objhttprequest.Proxy = proxyObject
objhttprequest.AllowAutoRedirect = True
objhttprequest.Timeout = 100000
objhttpresponse = objhttprequest.GetResponse
Dim objstrmreader As New StreamReader(objhttpresponse.GetResponseStream)
strReply = objstrmreader.ReadToEnd()
Catch ex2 As System.Net.WebException
GoTo tryAgain
Catch ex As Exception
strReply = "ERROR! " + ex.Message.ToString
GoTo tryAgain
End Try
Return strReply
End Function
What I got here is a vb.net code where I parse the website for its html
This function works fine.
The question is this...
1.If I run 100 threads with this function at the same time, Will it work?
2.Won't it affect my internet connection as well?
I don't want to waste time creating threads and codes a hundred times so if you know the answer please advice me on what should I do instead
One thing I see that could cause you problems is the goto. You retry if you get an error, but there is no way to break out of the method if an error does occur everytime you request the page, causing an infinite loop. You should put a check in, saying only try again if some cancel flag has not been set. Second, there could be issues with the number of threads you run depending on how much work each thread must do. There is a CPU and memory cost for each thread and it could peg your machine, especially if you get an infinite loop in one of them. Everything else gets a "it depends." Your pc and internet connection will determine everything else. There are tools available to monitor this and I would suggest using them to see what works. I found this page with a lot of information, it might have what you are looking for - http://www.slac.stanford.edu/xorg/nmtf/nmtf-tools.html. Hope this helps.
Wade