EvenTiles from Start to Finish - Part 13
Join the DZone community and get the full member experience.
Join For Freein the previous episode of this series about how to develop a windows phone application from scratch we fixed some issues to properly start and renew a periodictask . now we are ready to find out how an application can communicate with its periodictask.
in today’s eventiles episode, you will learn why you cannot simply use a variable to communicate between the application and the periodictask. in my opinion that is important, because understanding why some things are not working makes you a better windows phone developer and decreases the chance of having hard to trace bugs inside your own applications. in order to separate the functionality to transfer data between the application and its periodictask, we are going to create a new project inside the eventiles solution.
the project will be of type windows phone class library and we will call it eventilescomm . in its initial version, this class library will contain one single class with the name tiledata . it is used to store the text that the user can enter in the settings page of the eventiles application in order to allow the periodictask to display this string on the back of the secondary tile once it is created. in order to vary the text on the back of the secondary tile, tiledata will also contain a boolean variable indicating which string needs to be displayed on the secondary tile’s backside (either the string passed by the application or a default string that is defined inside the periodictask).
![]() |
to be able to access
tiledata
from within both the eventiles application and the periodictask, it
contains two static properties. a string property to store / retrieve
the message that is defined through the settings page and a boolean
property that defines which string needs to be displayed from within the
periodictask. the string property is always written by the application
and read by the periodictask. the boolean variable is both written by
the application and the periodictask but only read by the periodictask.
because of the fact that the periodictask and the application are
running inside their own, separate process in different threads, and
since they are running completely unsynchronized from each other, there
is a possibility that they both want to access one of the properties of
tiledata at the same time. to prevent this potential dangerous situation
(dangerous because it can leave the properties in an undefined state
when one of the two different threads want to access them while the
other is updating them), both properties are protected by a
mutex
synchronization object.
|
note: the following (initial) implementation of the tiledata class will not work properly, but it is shown here to help you understand what it means that an application and its periodictask belong to each other, but are completely separated from each other at the same time. you will have to wait a little while for a working solution, because that will be introduced in the next episode of eventiles.
threadsafe data access:
public class tiledata { private static mutex mtx = new mutex(false, "mtxsync"); private static string secondarybackcontent; private static bool showdefaultsecondarybackcontent; public static string secondarybackcontent { get { return retrievesecondarybackcontent(); } set { storesecondarybackcontent(value); } } public static bool showdefaultsecondarybackcontent { get { return retrieveshowdefaultsecondarybackcontent(); } set { storeshowdefaultsecondarybackcontent(value); } } private static string retrievesecondarybackcontent() { mtx.waitone(); try { return secondarybackcontent; } finally { mtx.releasemutex(); } } private static void storesecondarybackcontent(string content) { mtx.waitone(); try { secondarybackcontent = content; } finally { mtx.releasemutex(); } } private static bool retrieveshowdefaultsecondarybackcontent() { mtx.waitone(); try { return showdefaultsecondarybackcontent; } finally { mtx.releasemutex(); } } private static void storeshowdefaultsecondarybackcontent(bool showdefaultcontent) { mtx.waitone(); try { showdefaultsecondarybackcontent = showdefaultcontent; } finally { mtx.releasemutex(); } } }
if you look at the source code of the tiledata class, you can see that we are using a two properties through which we are calling a few private methods to actually store or retrieve data. you will also see that we define a single mutex inside the tiledata class. this mutex has a name, meaning it can be used to synchronize threads over multiple processes. this is important, since eventiles and its periodictask will execute in separate processes. if we take a look at one of the individual retrieval methods, you will see how the single mutex that is defined in tiledata is used.
retrieving data:
private static string retrievesecondarybackcontent() { mtx.waitone(); try { return secondarybackcontent; } finally { mtx.releasemutex(); } }
in this method, we access the variable secondarybackcontent only when the method waitone on our mutex returns. when waitone returns, our method has exclusive access to the variable secondarybackcontent until we call the method releasemutex on our mutex. at that moment, another thread that is waiting for the same mutex will be granted access. every method that uses of a mutex to get access to protected data must under all circumstances call releasemutex when it is done. that is the reason why we are adding a try / finally block. the code in the finally block will execute, even when exceptions are thrown. in this way, we prevent our application from a potential deadlock situations (where multiple threads are waiting on each other to free up a synchronization object that is never being freed).
the way data is protected for eventiles works properly, which can be verified by debugging the application and deliberately skipping a call to releasemutex from within the eventiles application (which is fully explained in the accompanying video as well). doing so will result in the periodictask waiting forever for the mutex, because it will never be released by the application. this at least proves that both eventiles and its periodictask are making use of the same mutex that they both need to own before being able to access variables.
there is still a potential problem, because we are calling the waitone method without parameters, which means that we will wait indefinitely until the mutex becomes available. in our simple example this is sufficient, but in a real application you most likely want to wait for a specific time and take action upon timeouts.
however, there is a way bigger problem with the current
implementation of our newly created tiledata class. we already saw that
the mutex is properly shared between eventiles and its periodictask, but
what about the public properties. the following screen dump shows you
what is wrong with the tiledata class right now. even though the
variable secondarybackcontent is set by the eventiles application, it
seems that it is not initialized when the periodictask retrieves the
variable (both through the appropriate properties).
since our eventiles application and its periodictask are running in
separate processes, they are completely separated from each other,
meaning that they get their own copies of variables they both want to
access, even though these variables are defined in a separate project.
this is a good thing (even though we have to solve the problem), because
otherwise all variables used by every process on the phone would need a
unique name. the following video shows eventiles in action in
combination with its periodictask. it shows how the mutex works and how
passing data fails.
to be able to experiment with this wrong implementation of eventiles,
especially to understand how the application interacts with the
periodictask, the sample code is available for
dowload here
.
instead of using ‘simple’ variables to pass data between eventiles and its periodictask, we will have to make use of isolatedstorage and have them share data through a file. that will be the topic of the next episode of eventiles.
source: http://mstruys.com/2012/01/08/eventiles-from-start-to-finishpart-13/
Opinions expressed by DZone contributors are their own.
Comments