Index: sems/apps/sw_vsc/SW_Vsc.cpp
===================================================================
--- sems.orig/apps/sw_vsc/SW_Vsc.cpp	2016-07-20 13:39:47.454933967 +0200
+++ sems/apps/sw_vsc/SW_Vsc.cpp	2016-07-20 14:32:19.535931094 +0200
@@ -93,6 +93,8 @@
     regfree(&m_patterns.speedDialPattern);
     regfree(&m_patterns.reminderOnPattern);
     regfree(&m_patterns.reminderOffPattern);
+    regfree(&m_patterns.blockinclirOnPattern);
+    regfree(&m_patterns.blockinclirOffPattern);
 }
 
 int SW_VscFactory::onLoad()
@@ -108,6 +110,8 @@
     string speedDialPattern;
     string reminderOnPattern;
     string reminderOffPattern;
+    string blockinclirOnPattern;
+    string blockinclirOffPattern;
 
     AmConfigReader cfg;
     if (cfg.loadFile(AmConfig::ModConfigPath + string(MOD_NAME ".conf")))
@@ -228,6 +232,18 @@
         ERROR("ReminderOffAnnouncement file not set\n");
         return -1;
     }
+    m_patterns.blockinclirOnAnnouncement = cfg.getParameter("blockinclir_on_announcement", "");
+    if (m_patterns.blockinclirOnAnnouncement.empty())
+    {
+        ERROR("BlockinclirOnAnnouncement file not set\n");
+        return -1;
+    }
+    m_patterns.blockinclirOffAnnouncement = cfg.getParameter("blockinclir_off_announcement", "");
+    if (m_patterns.blockinclirOffAnnouncement.empty())
+    {
+        ERROR("BlockinclirOffAnnouncement file not set\n");
+        return -1;
+    }
 
 
     m_patterns.voicemailNumber = cfg.getParameter("voicemail_number", "");
@@ -395,6 +411,36 @@
         return -1;
     }
 
+    blockinclirOnPattern = cfg.getParameter("blockinclir_on_pattern", "");
+    if (blockinclirOnPattern.empty())
+    {
+        ERROR("BlockinclirOnPattern is empty\n");
+        return -1;
+    }
+    if (regcomp(&m_patterns.blockinclirOnPattern, blockinclirOnPattern.c_str(), REG_EXTENDED | REG_NOSUB))
+    {
+        ERROR("BlockinclirOnPattern failed to compile ('%s'): %s\n",
+              blockinclirOnPattern.c_str(),
+              strerror(errno));
+        return -1;
+    }
+
+
+    blockinclirOffPattern = cfg.getParameter("blockinclir_off_pattern", "");
+    if (blockinclirOffPattern.empty())
+    {
+        ERROR("BlockinclirOffPattern is empty\n");
+        return -1;
+    }
+    if (regcomp(&m_patterns.blockinclirOffPattern, blockinclirOffPattern.c_str(),
+                REG_EXTENDED | REG_NOSUB))
+    {
+        ERROR("BlockinclirOffPattern failed to compile ('%s'): %s\n",
+              blockinclirOffPattern.c_str(),
+              strerror(errno));
+        return -1;
+    }
+
     return 0;
 }
 
@@ -1059,6 +1105,8 @@
     string speedDialAnnouncement;
     string reminderOnAnnouncement;
     string reminderOffAnnouncement;
+    string blockinclirOnAnnouncement;
+    string blockinclirOffAnnouncement;
 
     string uuid = getHeader(req.hdrs, "P-Caller-UUID");
     if (!uuid.length())
@@ -1177,6 +1225,22 @@
         filename = failAnnouncement;
         goto out;
     }
+    blockinclirOnAnnouncement = m_patterns->audioPath + lang + m_patterns->blockinclirOnAnnouncement;
+    if (!file_exists(blockinclirOnAnnouncement))
+    {
+        ERROR("BlockinclirOnAnnouncement file does not exist ('%s').\n",
+              blockinclirOnAnnouncement.c_str());
+        filename = failAnnouncement;
+        goto out;
+    }
+    blockinclirOffAnnouncement = m_patterns->audioPath + lang + m_patterns->blockinclirOffAnnouncement;
+    if (!file_exists(blockinclirOffAnnouncement))
+    {
+        ERROR("BlockinclirOffAnnouncement file does not exist ('%s').\n",
+              blockinclirOffAnnouncement.c_str());
+        filename = failAnnouncement;
+        goto out;
+    }
 
     my_handler = mysql_init(NULL);
     if (!mysql_real_connect(my_handler,
@@ -1842,6 +1906,95 @@
     }
 
 
+    // block in clir
+    if ((ret = regexec(&m_patterns->blockinclirOnPattern,
+                       req.user.c_str(), 0, 0, 0)) == 0)
+    {
+        std::string val = "1";
+        u_int64_t attId = getAttributeId(my_handler, "block_in_clir");
+        if (!attId)
+        {
+            filename = failAnnouncement;
+            goto out;
+        }
+        u_int64_t prefId = getPreference(my_handler, subId, attId,
+                                         &foundPref, &prefStr);
+        if (!prefId)
+        {
+            filename = failAnnouncement;
+            goto out;
+        }
+        else if (!foundPref)
+        {
+            if (!insertPreference(my_handler, subId, attId, val))
+            {
+                filename = failAnnouncement;
+                goto out;
+            }
+            INFO("Successfully set VSC block_in_clir for uuid '%s'",
+                 uuid.c_str());
+        }
+        else
+        {
+            if (!updatePreferenceId(my_handler, prefId, val))
+            {
+                filename = failAnnouncement;
+                goto out;
+            }
+            INFO("Successfully updated VSC block_in_clir for uuid '%s'",
+                 uuid.c_str());
+        }
+
+        filename = blockinclirOnAnnouncement;
+        goto out;
+    }
+    else if (ret != REG_NOMATCH)
+    {
+        filename = failAnnouncement;
+        goto out;
+    }
+
+    if ((ret = regexec(&m_patterns->blockinclirOffPattern,
+                       req.user.c_str(), 0, 0, 0)) == 0)
+    {
+        u_int64_t attId = getAttributeId(my_handler, "block_in_clir");
+        if (!attId)
+        {
+            filename = failAnnouncement;
+            goto out;
+        }
+        u_int64_t prefId = getPreference(my_handler, subId, attId,
+                                         &foundPref, &prefStr);
+        if (!prefId)
+        {
+            filename = failAnnouncement;
+            goto out;
+        }
+        else if (!foundPref)
+        {
+            INFO("Unnecessary VSC block_in_clir removal for uuid '%s'",
+                 uuid.c_str());
+        }
+        else if (!deletePreferenceId(my_handler, prefId))
+        {
+            filename = failAnnouncement;
+            goto out;
+        }
+        else
+        {
+            INFO("Successfully removed block_in_clir for uuid '%s'",
+                 uuid.c_str());
+        }
+
+        filename = blockinclirOffAnnouncement;
+        goto out;
+    }
+    else if (ret != REG_NOMATCH)
+    {
+        filename = failAnnouncement;
+        goto out;
+    }
+
 
     INFO("Unkown VSC code '%s' found", req.user.c_str());
     filename = unknownAnnouncement;
Index: sems/apps/sw_vsc/SW_Vsc.h
===================================================================
--- sems.orig/apps/sw_vsc/SW_Vsc.h	2016-07-20 13:39:47.402933680 +0200
+++ sems/apps/sw_vsc/SW_Vsc.h	2016-07-20 13:47:17.856976961 +0200
@@ -61,6 +61,12 @@
 
     regex_t reminderOffPattern;
     string reminderOffAnnouncement;
+
+    regex_t blockinclirOnPattern;
+    string blockinclirOnAnnouncement;
+
+    regex_t blockinclirOffPattern;
+    string blockinclirOffAnnouncement;
 } sw_vsc_patterns_t;
 
 class SW_VscFactory: public AmSessionFactory
Index: sems/apps/sw_vsc/etc/sw_vsc.conf
===================================================================
--- sems.orig/apps/sw_vsc/etc/sw_vsc.conf	2016-07-20 13:39:47.406933702 +0200
+++ sems/apps/sw_vsc/etc/sw_vsc.conf	2016-07-20 14:34:14.588367576 +0200
@@ -38,3 +38,8 @@
 reminder_off_pattern = ^(\%23)55(\%23)?.*$
 reminder_off_announcement = sw_vsc_deactivated.wav
 
+blockinclir_on_pattern = ^\*32\*$
+blockinclir_on_announcement = sw_vsc_activated.wav
+blockinclir_off_pattern = ^(\%23)32(\%23)?.*$
+blockinclir_off_announcement = sw_vsc_deactivated.wav
+
